1c66ac9dbSNicholas Bellinger /******************************************************************************* 2c66ac9dbSNicholas Bellinger * Filename: target_core_iblock.c 3c66ac9dbSNicholas Bellinger * 4c66ac9dbSNicholas Bellinger * This file contains the Storage Engine <-> Linux BlockIO transport 5c66ac9dbSNicholas Bellinger * specific functions. 6c66ac9dbSNicholas Bellinger * 74c76251eSNicholas Bellinger * (c) Copyright 2003-2013 Datera, Inc. 8c66ac9dbSNicholas Bellinger * 9c66ac9dbSNicholas Bellinger * Nicholas A. Bellinger <nab@kernel.org> 10c66ac9dbSNicholas Bellinger * 11c66ac9dbSNicholas Bellinger * This program is free software; you can redistribute it and/or modify 12c66ac9dbSNicholas Bellinger * it under the terms of the GNU General Public License as published by 13c66ac9dbSNicholas Bellinger * the Free Software Foundation; either version 2 of the License, or 14c66ac9dbSNicholas Bellinger * (at your option) any later version. 15c66ac9dbSNicholas Bellinger * 16c66ac9dbSNicholas Bellinger * This program is distributed in the hope that it will be useful, 17c66ac9dbSNicholas Bellinger * but WITHOUT ANY WARRANTY; without even the implied warranty of 18c66ac9dbSNicholas Bellinger * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 19c66ac9dbSNicholas Bellinger * GNU General Public License for more details. 20c66ac9dbSNicholas Bellinger * 21c66ac9dbSNicholas Bellinger * You should have received a copy of the GNU General Public License 22c66ac9dbSNicholas Bellinger * along with this program; if not, write to the Free Software 23c66ac9dbSNicholas Bellinger * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. 24c66ac9dbSNicholas Bellinger * 25c66ac9dbSNicholas Bellinger ******************************************************************************/ 26c66ac9dbSNicholas Bellinger 27c66ac9dbSNicholas Bellinger #include <linux/string.h> 28c66ac9dbSNicholas Bellinger #include <linux/parser.h> 29c66ac9dbSNicholas Bellinger #include <linux/timer.h> 30c66ac9dbSNicholas Bellinger #include <linux/fs.h> 31c66ac9dbSNicholas Bellinger #include <linux/blkdev.h> 32c66ac9dbSNicholas Bellinger #include <linux/slab.h> 33c66ac9dbSNicholas Bellinger #include <linux/spinlock.h> 34c66ac9dbSNicholas Bellinger #include <linux/bio.h> 35c66ac9dbSNicholas Bellinger #include <linux/genhd.h> 36c66ac9dbSNicholas Bellinger #include <linux/file.h> 37827509e3SPaul Gortmaker #include <linux/module.h> 38ba929992SBart Van Assche #include <scsi/scsi_proto.h> 3914150a6bSChristoph Hellwig #include <asm/unaligned.h> 40c66ac9dbSNicholas Bellinger 41c66ac9dbSNicholas Bellinger #include <target/target_core_base.h> 42c4795fb2SChristoph Hellwig #include <target/target_core_backend.h> 43c66ac9dbSNicholas Bellinger 44c66ac9dbSNicholas Bellinger #include "target_core_iblock.h" 45c66ac9dbSNicholas Bellinger 46d5b4a21bSChristoph Hellwig #define IBLOCK_MAX_BIO_PER_TASK 32 /* max # of bios to submit at a time */ 47d5b4a21bSChristoph Hellwig #define IBLOCK_BIO_POOL_SIZE 128 48d5b4a21bSChristoph Hellwig 490fd97ccfSChristoph Hellwig static inline struct iblock_dev *IBLOCK_DEV(struct se_device *dev) 500fd97ccfSChristoph Hellwig { 510fd97ccfSChristoph Hellwig return container_of(dev, struct iblock_dev, dev); 520fd97ccfSChristoph Hellwig } 530fd97ccfSChristoph Hellwig 540fd97ccfSChristoph Hellwig 55c66ac9dbSNicholas Bellinger static int iblock_attach_hba(struct se_hba *hba, u32 host_id) 56c66ac9dbSNicholas Bellinger { 576708bb27SAndy Grover pr_debug("CORE_HBA[%d] - TCM iBlock HBA Driver %s on" 58c66ac9dbSNicholas Bellinger " Generic Target Core Stack %s\n", hba->hba_id, 59ce8dd25dSChristoph Hellwig IBLOCK_VERSION, TARGET_CORE_VERSION); 60c66ac9dbSNicholas Bellinger return 0; 61c66ac9dbSNicholas Bellinger } 62c66ac9dbSNicholas Bellinger 63c66ac9dbSNicholas Bellinger static void iblock_detach_hba(struct se_hba *hba) 64c66ac9dbSNicholas Bellinger { 65c66ac9dbSNicholas Bellinger } 66c66ac9dbSNicholas Bellinger 670fd97ccfSChristoph Hellwig static struct se_device *iblock_alloc_device(struct se_hba *hba, const char *name) 68c66ac9dbSNicholas Bellinger { 69c66ac9dbSNicholas Bellinger struct iblock_dev *ib_dev = NULL; 70c66ac9dbSNicholas Bellinger 71c66ac9dbSNicholas Bellinger ib_dev = kzalloc(sizeof(struct iblock_dev), GFP_KERNEL); 726708bb27SAndy Grover if (!ib_dev) { 736708bb27SAndy Grover pr_err("Unable to allocate struct iblock_dev\n"); 74c66ac9dbSNicholas Bellinger return NULL; 75c66ac9dbSNicholas Bellinger } 76c66ac9dbSNicholas Bellinger 776708bb27SAndy Grover pr_debug( "IBLOCK: Allocated ib_dev for %s\n", name); 78c66ac9dbSNicholas Bellinger 790fd97ccfSChristoph Hellwig return &ib_dev->dev; 80c66ac9dbSNicholas Bellinger } 81c66ac9dbSNicholas Bellinger 820fd97ccfSChristoph Hellwig static int iblock_configure_device(struct se_device *dev) 83c66ac9dbSNicholas Bellinger { 840fd97ccfSChristoph Hellwig struct iblock_dev *ib_dev = IBLOCK_DEV(dev); 85c66ac9dbSNicholas Bellinger struct request_queue *q; 860fd97ccfSChristoph Hellwig struct block_device *bd = NULL; 87ecebbf6cSNicholas Bellinger struct blk_integrity *bi; 8844bfd018SAndy Grover fmode_t mode; 890fd97ccfSChristoph Hellwig int ret = -ENOMEM; 90c66ac9dbSNicholas Bellinger 910fd97ccfSChristoph Hellwig if (!(ib_dev->ibd_flags & IBDF_HAS_UDEV_PATH)) { 920fd97ccfSChristoph Hellwig pr_err("Missing udev_path= parameters for IBLOCK\n"); 930fd97ccfSChristoph Hellwig return -EINVAL; 94c66ac9dbSNicholas Bellinger } 95d5b4a21bSChristoph Hellwig 96d5b4a21bSChristoph Hellwig ib_dev->ibd_bio_set = bioset_create(IBLOCK_BIO_POOL_SIZE, 0); 976708bb27SAndy Grover if (!ib_dev->ibd_bio_set) { 980fd97ccfSChristoph Hellwig pr_err("IBLOCK: Unable to create bioset\n"); 990fd97ccfSChristoph Hellwig goto out; 100c66ac9dbSNicholas Bellinger } 1010fd97ccfSChristoph Hellwig 1026708bb27SAndy Grover pr_debug( "IBLOCK: Claiming struct block_device: %s\n", 103c66ac9dbSNicholas Bellinger ib_dev->ibd_udev_path); 104c66ac9dbSNicholas Bellinger 10544bfd018SAndy Grover mode = FMODE_READ|FMODE_EXCL; 10644bfd018SAndy Grover if (!ib_dev->ibd_readonly) 10744bfd018SAndy Grover mode |= FMODE_WRITE; 108eeeb9522SNicholas Bellinger else 109eeeb9522SNicholas Bellinger dev->dev_flags |= DF_READ_ONLY; 11044bfd018SAndy Grover 11144bfd018SAndy Grover bd = blkdev_get_by_path(ib_dev->ibd_udev_path, mode, ib_dev); 112613640e4SNicholas Bellinger if (IS_ERR(bd)) { 113613640e4SNicholas Bellinger ret = PTR_ERR(bd); 1140fd97ccfSChristoph Hellwig goto out_free_bioset; 115613640e4SNicholas Bellinger } 116c66ac9dbSNicholas Bellinger ib_dev->ibd_bd = bd; 117c66ac9dbSNicholas Bellinger 1180fd97ccfSChristoph Hellwig q = bdev_get_queue(bd); 1190fd97ccfSChristoph Hellwig 1200fd97ccfSChristoph Hellwig dev->dev_attrib.hw_block_size = bdev_logical_block_size(bd); 121046ba642SNicholas Bellinger dev->dev_attrib.hw_max_sectors = queue_max_hw_sectors(q); 1220fd97ccfSChristoph Hellwig dev->dev_attrib.hw_queue_depth = q->nr_requests; 123c66ac9dbSNicholas Bellinger 1248a9ebe71SMike Christie if (target_configure_unmap_from_queue(&dev->dev_attrib, q, 1258a9ebe71SMike Christie dev->dev_attrib.hw_block_size)) 1266708bb27SAndy Grover pr_debug("IBLOCK: BLOCK Discard support available," 127c66ac9dbSNicholas Bellinger " disabled by default\n"); 1288a9ebe71SMike Christie 129f6970ad3SNicholas Bellinger /* 130f6970ad3SNicholas Bellinger * Enable write same emulation for IBLOCK and use 0xFFFF as 131f6970ad3SNicholas Bellinger * the smaller WRITE_SAME(10) only has a two-byte block count. 132f6970ad3SNicholas Bellinger */ 133f6970ad3SNicholas Bellinger dev->dev_attrib.max_write_same_len = 0xFFFF; 134c66ac9dbSNicholas Bellinger 135e22a7f07SRoland Dreier if (blk_queue_nonrot(q)) 1360fd97ccfSChristoph Hellwig dev->dev_attrib.is_nonrot = 1; 137d0c8b259SNicholas Bellinger 138ecebbf6cSNicholas Bellinger bi = bdev_get_integrity(bd); 139ecebbf6cSNicholas Bellinger if (bi) { 140ecebbf6cSNicholas Bellinger struct bio_set *bs = ib_dev->ibd_bio_set; 141ecebbf6cSNicholas Bellinger 1420f8087ecSMartin K. Petersen if (!strcmp(bi->profile->name, "T10-DIF-TYPE3-IP") || 1430f8087ecSMartin K. Petersen !strcmp(bi->profile->name, "T10-DIF-TYPE1-IP")) { 144ecebbf6cSNicholas Bellinger pr_err("IBLOCK export of blk_integrity: %s not" 1450f8087ecSMartin K. Petersen " supported\n", bi->profile->name); 146ecebbf6cSNicholas Bellinger ret = -ENOSYS; 147ecebbf6cSNicholas Bellinger goto out_blkdev_put; 148ecebbf6cSNicholas Bellinger } 149ecebbf6cSNicholas Bellinger 1500f8087ecSMartin K. Petersen if (!strcmp(bi->profile->name, "T10-DIF-TYPE3-CRC")) { 151ecebbf6cSNicholas Bellinger dev->dev_attrib.pi_prot_type = TARGET_DIF_TYPE3_PROT; 1520f8087ecSMartin K. Petersen } else if (!strcmp(bi->profile->name, "T10-DIF-TYPE1-CRC")) { 153ecebbf6cSNicholas Bellinger dev->dev_attrib.pi_prot_type = TARGET_DIF_TYPE1_PROT; 154ecebbf6cSNicholas Bellinger } 155ecebbf6cSNicholas Bellinger 156ecebbf6cSNicholas Bellinger if (dev->dev_attrib.pi_prot_type) { 157ecebbf6cSNicholas Bellinger if (bioset_integrity_create(bs, IBLOCK_BIO_POOL_SIZE) < 0) { 158ecebbf6cSNicholas Bellinger pr_err("Unable to allocate bioset for PI\n"); 159ecebbf6cSNicholas Bellinger ret = -ENOMEM; 160ecebbf6cSNicholas Bellinger goto out_blkdev_put; 161ecebbf6cSNicholas Bellinger } 162ecebbf6cSNicholas Bellinger pr_debug("IBLOCK setup BIP bs->bio_integrity_pool: %p\n", 163ecebbf6cSNicholas Bellinger bs->bio_integrity_pool); 164ecebbf6cSNicholas Bellinger } 165ecebbf6cSNicholas Bellinger dev->dev_attrib.hw_pi_prot_type = dev->dev_attrib.pi_prot_type; 166ecebbf6cSNicholas Bellinger } 167ecebbf6cSNicholas Bellinger 1680fd97ccfSChristoph Hellwig return 0; 169e22a7f07SRoland Dreier 170ecebbf6cSNicholas Bellinger out_blkdev_put: 171ecebbf6cSNicholas Bellinger blkdev_put(ib_dev->ibd_bd, FMODE_WRITE|FMODE_READ|FMODE_EXCL); 1720fd97ccfSChristoph Hellwig out_free_bioset: 173c66ac9dbSNicholas Bellinger bioset_free(ib_dev->ibd_bio_set); 174c66ac9dbSNicholas Bellinger ib_dev->ibd_bio_set = NULL; 1750fd97ccfSChristoph Hellwig out: 1760fd97ccfSChristoph Hellwig return ret; 177c66ac9dbSNicholas Bellinger } 178c66ac9dbSNicholas Bellinger 1794cc987eaSNicholas Bellinger static void iblock_dev_call_rcu(struct rcu_head *p) 1804cc987eaSNicholas Bellinger { 1814cc987eaSNicholas Bellinger struct se_device *dev = container_of(p, struct se_device, rcu_head); 1824cc987eaSNicholas Bellinger struct iblock_dev *ib_dev = IBLOCK_DEV(dev); 1834cc987eaSNicholas Bellinger 1844cc987eaSNicholas Bellinger kfree(ib_dev); 1854cc987eaSNicholas Bellinger } 1864cc987eaSNicholas Bellinger 1870fd97ccfSChristoph Hellwig static void iblock_free_device(struct se_device *dev) 188c66ac9dbSNicholas Bellinger { 1890fd97ccfSChristoph Hellwig struct iblock_dev *ib_dev = IBLOCK_DEV(dev); 190c66ac9dbSNicholas Bellinger 191bc665524SNicholas Bellinger if (ib_dev->ibd_bd != NULL) 192c66ac9dbSNicholas Bellinger blkdev_put(ib_dev->ibd_bd, FMODE_WRITE|FMODE_READ|FMODE_EXCL); 193d84287bcSNicholas Bellinger if (ib_dev->ibd_bio_set != NULL) 194c66ac9dbSNicholas Bellinger bioset_free(ib_dev->ibd_bio_set); 195d84287bcSNicholas Bellinger 1964cc987eaSNicholas Bellinger call_rcu(&dev->rcu_head, iblock_dev_call_rcu); 197c66ac9dbSNicholas Bellinger } 198c66ac9dbSNicholas Bellinger 199c66ac9dbSNicholas Bellinger static unsigned long long iblock_emulate_read_cap_with_block_size( 200c66ac9dbSNicholas Bellinger struct se_device *dev, 201c66ac9dbSNicholas Bellinger struct block_device *bd, 202c66ac9dbSNicholas Bellinger struct request_queue *q) 203c66ac9dbSNicholas Bellinger { 204c66ac9dbSNicholas Bellinger unsigned long long blocks_long = (div_u64(i_size_read(bd->bd_inode), 205c66ac9dbSNicholas Bellinger bdev_logical_block_size(bd)) - 1); 206c66ac9dbSNicholas Bellinger u32 block_size = bdev_logical_block_size(bd); 207c66ac9dbSNicholas Bellinger 2080fd97ccfSChristoph Hellwig if (block_size == dev->dev_attrib.block_size) 209c66ac9dbSNicholas Bellinger return blocks_long; 210c66ac9dbSNicholas Bellinger 211c66ac9dbSNicholas Bellinger switch (block_size) { 212c66ac9dbSNicholas Bellinger case 4096: 2130fd97ccfSChristoph Hellwig switch (dev->dev_attrib.block_size) { 214c66ac9dbSNicholas Bellinger case 2048: 215c66ac9dbSNicholas Bellinger blocks_long <<= 1; 216c66ac9dbSNicholas Bellinger break; 217c66ac9dbSNicholas Bellinger case 1024: 218c66ac9dbSNicholas Bellinger blocks_long <<= 2; 219c66ac9dbSNicholas Bellinger break; 220c66ac9dbSNicholas Bellinger case 512: 221c66ac9dbSNicholas Bellinger blocks_long <<= 3; 222c66ac9dbSNicholas Bellinger default: 223c66ac9dbSNicholas Bellinger break; 224c66ac9dbSNicholas Bellinger } 225c66ac9dbSNicholas Bellinger break; 226c66ac9dbSNicholas Bellinger case 2048: 2270fd97ccfSChristoph Hellwig switch (dev->dev_attrib.block_size) { 228c66ac9dbSNicholas Bellinger case 4096: 229c66ac9dbSNicholas Bellinger blocks_long >>= 1; 230c66ac9dbSNicholas Bellinger break; 231c66ac9dbSNicholas Bellinger case 1024: 232c66ac9dbSNicholas Bellinger blocks_long <<= 1; 233c66ac9dbSNicholas Bellinger break; 234c66ac9dbSNicholas Bellinger case 512: 235c66ac9dbSNicholas Bellinger blocks_long <<= 2; 236c66ac9dbSNicholas Bellinger break; 237c66ac9dbSNicholas Bellinger default: 238c66ac9dbSNicholas Bellinger break; 239c66ac9dbSNicholas Bellinger } 240c66ac9dbSNicholas Bellinger break; 241c66ac9dbSNicholas Bellinger case 1024: 2420fd97ccfSChristoph Hellwig switch (dev->dev_attrib.block_size) { 243c66ac9dbSNicholas Bellinger case 4096: 244c66ac9dbSNicholas Bellinger blocks_long >>= 2; 245c66ac9dbSNicholas Bellinger break; 246c66ac9dbSNicholas Bellinger case 2048: 247c66ac9dbSNicholas Bellinger blocks_long >>= 1; 248c66ac9dbSNicholas Bellinger break; 249c66ac9dbSNicholas Bellinger case 512: 250c66ac9dbSNicholas Bellinger blocks_long <<= 1; 251c66ac9dbSNicholas Bellinger break; 252c66ac9dbSNicholas Bellinger default: 253c66ac9dbSNicholas Bellinger break; 254c66ac9dbSNicholas Bellinger } 255c66ac9dbSNicholas Bellinger break; 256c66ac9dbSNicholas Bellinger case 512: 2570fd97ccfSChristoph Hellwig switch (dev->dev_attrib.block_size) { 258c66ac9dbSNicholas Bellinger case 4096: 259c66ac9dbSNicholas Bellinger blocks_long >>= 3; 260c66ac9dbSNicholas Bellinger break; 261c66ac9dbSNicholas Bellinger case 2048: 262c66ac9dbSNicholas Bellinger blocks_long >>= 2; 263c66ac9dbSNicholas Bellinger break; 264c66ac9dbSNicholas Bellinger case 1024: 265c66ac9dbSNicholas Bellinger blocks_long >>= 1; 266c66ac9dbSNicholas Bellinger break; 267c66ac9dbSNicholas Bellinger default: 268c66ac9dbSNicholas Bellinger break; 269c66ac9dbSNicholas Bellinger } 270c66ac9dbSNicholas Bellinger break; 271c66ac9dbSNicholas Bellinger default: 272c66ac9dbSNicholas Bellinger break; 273c66ac9dbSNicholas Bellinger } 274c66ac9dbSNicholas Bellinger 275c66ac9dbSNicholas Bellinger return blocks_long; 276c66ac9dbSNicholas Bellinger } 277c66ac9dbSNicholas Bellinger 2783a41d85fSNicholas Bellinger static void iblock_complete_cmd(struct se_cmd *cmd) 2793a41d85fSNicholas Bellinger { 2803a41d85fSNicholas Bellinger struct iblock_req *ibr = cmd->priv; 2813a41d85fSNicholas Bellinger u8 status; 2823a41d85fSNicholas Bellinger 2833a41d85fSNicholas Bellinger if (!atomic_dec_and_test(&ibr->pending)) 2843a41d85fSNicholas Bellinger return; 2853a41d85fSNicholas Bellinger 2863a41d85fSNicholas Bellinger if (atomic_read(&ibr->ib_bio_err_cnt)) 2873a41d85fSNicholas Bellinger status = SAM_STAT_CHECK_CONDITION; 2883a41d85fSNicholas Bellinger else 2893a41d85fSNicholas Bellinger status = SAM_STAT_GOOD; 2903a41d85fSNicholas Bellinger 2913a41d85fSNicholas Bellinger target_complete_cmd(cmd, status); 2923a41d85fSNicholas Bellinger kfree(ibr); 2933a41d85fSNicholas Bellinger } 2943a41d85fSNicholas Bellinger 2954246a0b6SChristoph Hellwig static void iblock_bio_done(struct bio *bio) 2963a41d85fSNicholas Bellinger { 2973a41d85fSNicholas Bellinger struct se_cmd *cmd = bio->bi_private; 2983a41d85fSNicholas Bellinger struct iblock_req *ibr = cmd->priv; 2993a41d85fSNicholas Bellinger 3004246a0b6SChristoph Hellwig if (bio->bi_error) { 3014246a0b6SChristoph Hellwig pr_err("bio error: %p, err: %d\n", bio, bio->bi_error); 3023a41d85fSNicholas Bellinger /* 3033a41d85fSNicholas Bellinger * Bump the ib_bio_err_cnt and release bio. 3043a41d85fSNicholas Bellinger */ 3053a41d85fSNicholas Bellinger atomic_inc(&ibr->ib_bio_err_cnt); 3064e857c58SPeter Zijlstra smp_mb__after_atomic(); 3073a41d85fSNicholas Bellinger } 3083a41d85fSNicholas Bellinger 3093a41d85fSNicholas Bellinger bio_put(bio); 3103a41d85fSNicholas Bellinger 3113a41d85fSNicholas Bellinger iblock_complete_cmd(cmd); 3123a41d85fSNicholas Bellinger } 3133a41d85fSNicholas Bellinger 3143a41d85fSNicholas Bellinger static struct bio * 3154e49ea4aSMike Christie iblock_get_bio(struct se_cmd *cmd, sector_t lba, u32 sg_num, int rw) 3163a41d85fSNicholas Bellinger { 3173a41d85fSNicholas Bellinger struct iblock_dev *ib_dev = IBLOCK_DEV(cmd->se_dev); 3183a41d85fSNicholas Bellinger struct bio *bio; 3193a41d85fSNicholas Bellinger 3203a41d85fSNicholas Bellinger /* 3213a41d85fSNicholas Bellinger * Only allocate as many vector entries as the bio code allows us to, 3223a41d85fSNicholas Bellinger * we'll loop later on until we have handled the whole request. 3233a41d85fSNicholas Bellinger */ 3243a41d85fSNicholas Bellinger if (sg_num > BIO_MAX_PAGES) 3253a41d85fSNicholas Bellinger sg_num = BIO_MAX_PAGES; 3263a41d85fSNicholas Bellinger 3273a41d85fSNicholas Bellinger bio = bio_alloc_bioset(GFP_NOIO, sg_num, ib_dev->ibd_bio_set); 3283a41d85fSNicholas Bellinger if (!bio) { 3293a41d85fSNicholas Bellinger pr_err("Unable to allocate memory for bio\n"); 3303a41d85fSNicholas Bellinger return NULL; 3313a41d85fSNicholas Bellinger } 3323a41d85fSNicholas Bellinger 3333a41d85fSNicholas Bellinger bio->bi_bdev = ib_dev->ibd_bd; 3343a41d85fSNicholas Bellinger bio->bi_private = cmd; 3353a41d85fSNicholas Bellinger bio->bi_end_io = &iblock_bio_done; 3364f024f37SKent Overstreet bio->bi_iter.bi_sector = lba; 3374e49ea4aSMike Christie bio->bi_rw = rw; 3383a41d85fSNicholas Bellinger 3393a41d85fSNicholas Bellinger return bio; 3403a41d85fSNicholas Bellinger } 3413a41d85fSNicholas Bellinger 3424e49ea4aSMike Christie static void iblock_submit_bios(struct bio_list *list) 3433a41d85fSNicholas Bellinger { 3443a41d85fSNicholas Bellinger struct blk_plug plug; 3453a41d85fSNicholas Bellinger struct bio *bio; 3463a41d85fSNicholas Bellinger 3473a41d85fSNicholas Bellinger blk_start_plug(&plug); 3483a41d85fSNicholas Bellinger while ((bio = bio_list_pop(list))) 3494e49ea4aSMike Christie submit_bio(bio); 3503a41d85fSNicholas Bellinger blk_finish_plug(&plug); 3513a41d85fSNicholas Bellinger } 3523a41d85fSNicholas Bellinger 3534246a0b6SChristoph Hellwig static void iblock_end_io_flush(struct bio *bio) 354df5fa691SChristoph Hellwig { 355df5fa691SChristoph Hellwig struct se_cmd *cmd = bio->bi_private; 356df5fa691SChristoph Hellwig 3574246a0b6SChristoph Hellwig if (bio->bi_error) 3584246a0b6SChristoph Hellwig pr_err("IBLOCK: cache flush failed: %d\n", bio->bi_error); 359df5fa691SChristoph Hellwig 3605787cacdSChristoph Hellwig if (cmd) { 3614246a0b6SChristoph Hellwig if (bio->bi_error) 3625787cacdSChristoph Hellwig target_complete_cmd(cmd, SAM_STAT_CHECK_CONDITION); 363de103c93SChristoph Hellwig else 3645787cacdSChristoph Hellwig target_complete_cmd(cmd, SAM_STAT_GOOD); 3655787cacdSChristoph Hellwig } 3665787cacdSChristoph Hellwig 367df5fa691SChristoph Hellwig bio_put(bio); 368df5fa691SChristoph Hellwig } 369df5fa691SChristoph Hellwig 370c66ac9dbSNicholas Bellinger /* 371df5fa691SChristoph Hellwig * Implement SYCHRONIZE CACHE. Note that we can't handle lba ranges and must 372df5fa691SChristoph Hellwig * always flush the whole cache. 373c66ac9dbSNicholas Bellinger */ 374de103c93SChristoph Hellwig static sense_reason_t 375de103c93SChristoph Hellwig iblock_execute_sync_cache(struct se_cmd *cmd) 376c66ac9dbSNicholas Bellinger { 3770fd97ccfSChristoph Hellwig struct iblock_dev *ib_dev = IBLOCK_DEV(cmd->se_dev); 378a1d8b49aSAndy Grover int immed = (cmd->t_task_cdb[1] & 0x2); 379df5fa691SChristoph Hellwig struct bio *bio; 380c66ac9dbSNicholas Bellinger 381c66ac9dbSNicholas Bellinger /* 382c66ac9dbSNicholas Bellinger * If the Immediate bit is set, queue up the GOOD response 383df5fa691SChristoph Hellwig * for this SYNCHRONIZE_CACHE op. 384c66ac9dbSNicholas Bellinger */ 385c66ac9dbSNicholas Bellinger if (immed) 3865787cacdSChristoph Hellwig target_complete_cmd(cmd, SAM_STAT_GOOD); 387c66ac9dbSNicholas Bellinger 388df5fa691SChristoph Hellwig bio = bio_alloc(GFP_KERNEL, 0); 389df5fa691SChristoph Hellwig bio->bi_end_io = iblock_end_io_flush; 390df5fa691SChristoph Hellwig bio->bi_bdev = ib_dev->ibd_bd; 3914e49ea4aSMike Christie bio->bi_rw = WRITE_FLUSH; 392c66ac9dbSNicholas Bellinger if (!immed) 393df5fa691SChristoph Hellwig bio->bi_private = cmd; 3944e49ea4aSMike Christie submit_bio(bio); 395ad67f0d9SChristoph Hellwig return 0; 396c66ac9dbSNicholas Bellinger } 397c66ac9dbSNicholas Bellinger 398de103c93SChristoph Hellwig static sense_reason_t 39962e46942SChristoph Hellwig iblock_execute_unmap(struct se_cmd *cmd, sector_t lba, sector_t nolb) 400dbc21c5aSAsias He { 40162e46942SChristoph Hellwig struct block_device *bdev = IBLOCK_DEV(cmd->se_dev)->ibd_bd; 4028a9ebe71SMike Christie struct se_device *dev = cmd->se_dev; 403dbc21c5aSAsias He int ret; 404dbc21c5aSAsias He 4058a9ebe71SMike Christie ret = blkdev_issue_discard(bdev, 4068a9ebe71SMike Christie target_to_linux_sector(dev, lba), 4078a9ebe71SMike Christie target_to_linux_sector(dev, nolb), 4088a9ebe71SMike Christie GFP_KERNEL, 0); 409dbc21c5aSAsias He if (ret < 0) { 410dbc21c5aSAsias He pr_err("blkdev_issue_discard() failed: %d\n", ret); 411dbc21c5aSAsias He return TCM_LOGICAL_UNIT_COMMUNICATION_FAILURE; 412dbc21c5aSAsias He } 413dbc21c5aSAsias He 414dbc21c5aSAsias He return 0; 415dbc21c5aSAsias He } 416dbc21c5aSAsias He 417dbc21c5aSAsias He static sense_reason_t 41807b63196SMike Christie iblock_execute_write_same_direct(struct block_device *bdev, struct se_cmd *cmd) 41907b63196SMike Christie { 42007b63196SMike Christie struct se_device *dev = cmd->se_dev; 42107b63196SMike Christie struct scatterlist *sg = &cmd->t_data_sg[0]; 42207b63196SMike Christie struct page *page = NULL; 42307b63196SMike Christie int ret; 42407b63196SMike Christie 42507b63196SMike Christie if (sg->offset) { 42607b63196SMike Christie page = alloc_page(GFP_KERNEL); 42707b63196SMike Christie if (!page) 42807b63196SMike Christie return TCM_OUT_OF_RESOURCES; 42907b63196SMike Christie sg_copy_to_buffer(sg, cmd->t_data_nents, page_address(page), 43007b63196SMike Christie dev->dev_attrib.block_size); 43107b63196SMike Christie } 43207b63196SMike Christie 43307b63196SMike Christie ret = blkdev_issue_write_same(bdev, 43407b63196SMike Christie target_to_linux_sector(dev, cmd->t_task_lba), 43507b63196SMike Christie target_to_linux_sector(dev, 43607b63196SMike Christie sbc_get_write_same_sectors(cmd)), 43707b63196SMike Christie GFP_KERNEL, page ? page : sg_page(sg)); 43807b63196SMike Christie if (page) 43907b63196SMike Christie __free_page(page); 44007b63196SMike Christie if (ret) 44107b63196SMike Christie return TCM_LOGICAL_UNIT_COMMUNICATION_FAILURE; 44207b63196SMike Christie 44307b63196SMike Christie target_complete_cmd(cmd, GOOD); 44407b63196SMike Christie return 0; 44507b63196SMike Christie } 44607b63196SMike Christie 44707b63196SMike Christie static sense_reason_t 448f6970ad3SNicholas Bellinger iblock_execute_write_same(struct se_cmd *cmd) 449f6970ad3SNicholas Bellinger { 45007b63196SMike Christie struct block_device *bdev = IBLOCK_DEV(cmd->se_dev)->ibd_bd; 451f6970ad3SNicholas Bellinger struct iblock_req *ibr; 452f6970ad3SNicholas Bellinger struct scatterlist *sg; 453f6970ad3SNicholas Bellinger struct bio *bio; 454f6970ad3SNicholas Bellinger struct bio_list list; 4558a9ebe71SMike Christie struct se_device *dev = cmd->se_dev; 4568a9ebe71SMike Christie sector_t block_lba = target_to_linux_sector(dev, cmd->t_task_lba); 4578a9ebe71SMike Christie sector_t sectors = target_to_linux_sector(dev, 4588a9ebe71SMike Christie sbc_get_write_same_sectors(cmd)); 459f6970ad3SNicholas Bellinger 460afd73f1bSNicholas Bellinger if (cmd->prot_op) { 461afd73f1bSNicholas Bellinger pr_err("WRITE_SAME: Protection information with IBLOCK" 462afd73f1bSNicholas Bellinger " backends not supported\n"); 463afd73f1bSNicholas Bellinger return TCM_LOGICAL_UNIT_COMMUNICATION_FAILURE; 464afd73f1bSNicholas Bellinger } 465f6970ad3SNicholas Bellinger sg = &cmd->t_data_sg[0]; 466f6970ad3SNicholas Bellinger 467f6970ad3SNicholas Bellinger if (cmd->t_data_nents > 1 || 468f6970ad3SNicholas Bellinger sg->length != cmd->se_dev->dev_attrib.block_size) { 469f6970ad3SNicholas Bellinger pr_err("WRITE_SAME: Illegal SGL t_data_nents: %u length: %u" 470f6970ad3SNicholas Bellinger " block_size: %u\n", cmd->t_data_nents, sg->length, 471f6970ad3SNicholas Bellinger cmd->se_dev->dev_attrib.block_size); 472f6970ad3SNicholas Bellinger return TCM_INVALID_CDB_FIELD; 473f6970ad3SNicholas Bellinger } 474f6970ad3SNicholas Bellinger 47507b63196SMike Christie if (bdev_write_same(bdev)) 47607b63196SMike Christie return iblock_execute_write_same_direct(bdev, cmd); 47707b63196SMike Christie 478f6970ad3SNicholas Bellinger ibr = kzalloc(sizeof(struct iblock_req), GFP_KERNEL); 479f6970ad3SNicholas Bellinger if (!ibr) 480f6970ad3SNicholas Bellinger goto fail; 481f6970ad3SNicholas Bellinger cmd->priv = ibr; 482f6970ad3SNicholas Bellinger 4834e49ea4aSMike Christie bio = iblock_get_bio(cmd, block_lba, 1, WRITE); 484f6970ad3SNicholas Bellinger if (!bio) 485f6970ad3SNicholas Bellinger goto fail_free_ibr; 486f6970ad3SNicholas Bellinger 487f6970ad3SNicholas Bellinger bio_list_init(&list); 488f6970ad3SNicholas Bellinger bio_list_add(&list, bio); 489f6970ad3SNicholas Bellinger 490f6970ad3SNicholas Bellinger atomic_set(&ibr->pending, 1); 491f6970ad3SNicholas Bellinger 492f6970ad3SNicholas Bellinger while (sectors) { 493f6970ad3SNicholas Bellinger while (bio_add_page(bio, sg_page(sg), sg->length, sg->offset) 494f6970ad3SNicholas Bellinger != sg->length) { 495f6970ad3SNicholas Bellinger 4964e49ea4aSMike Christie bio = iblock_get_bio(cmd, block_lba, 1, WRITE); 497f6970ad3SNicholas Bellinger if (!bio) 498f6970ad3SNicholas Bellinger goto fail_put_bios; 499f6970ad3SNicholas Bellinger 500f6970ad3SNicholas Bellinger atomic_inc(&ibr->pending); 501f6970ad3SNicholas Bellinger bio_list_add(&list, bio); 502f6970ad3SNicholas Bellinger } 503f6970ad3SNicholas Bellinger 504f6970ad3SNicholas Bellinger /* Always in 512 byte units for Linux/Block */ 505f6970ad3SNicholas Bellinger block_lba += sg->length >> IBLOCK_LBA_SHIFT; 506f6970ad3SNicholas Bellinger sectors -= 1; 507f6970ad3SNicholas Bellinger } 508f6970ad3SNicholas Bellinger 5094e49ea4aSMike Christie iblock_submit_bios(&list); 510f6970ad3SNicholas Bellinger return 0; 511f6970ad3SNicholas Bellinger 512f6970ad3SNicholas Bellinger fail_put_bios: 513f6970ad3SNicholas Bellinger while ((bio = bio_list_pop(&list))) 514f6970ad3SNicholas Bellinger bio_put(bio); 515f6970ad3SNicholas Bellinger fail_free_ibr: 516f6970ad3SNicholas Bellinger kfree(ibr); 517f6970ad3SNicholas Bellinger fail: 518f6970ad3SNicholas Bellinger return TCM_LOGICAL_UNIT_COMMUNICATION_FAILURE; 519f6970ad3SNicholas Bellinger } 520f6970ad3SNicholas Bellinger 521c66ac9dbSNicholas Bellinger enum { 52244bfd018SAndy Grover Opt_udev_path, Opt_readonly, Opt_force, Opt_err 523c66ac9dbSNicholas Bellinger }; 524c66ac9dbSNicholas Bellinger 525c66ac9dbSNicholas Bellinger static match_table_t tokens = { 526c66ac9dbSNicholas Bellinger {Opt_udev_path, "udev_path=%s"}, 52744bfd018SAndy Grover {Opt_readonly, "readonly=%d"}, 528c66ac9dbSNicholas Bellinger {Opt_force, "force=%d"}, 529c66ac9dbSNicholas Bellinger {Opt_err, NULL} 530c66ac9dbSNicholas Bellinger }; 531c66ac9dbSNicholas Bellinger 5320fd97ccfSChristoph Hellwig static ssize_t iblock_set_configfs_dev_params(struct se_device *dev, 533c66ac9dbSNicholas Bellinger const char *page, ssize_t count) 534c66ac9dbSNicholas Bellinger { 5350fd97ccfSChristoph Hellwig struct iblock_dev *ib_dev = IBLOCK_DEV(dev); 5366d180253SJesper Juhl char *orig, *ptr, *arg_p, *opts; 537c66ac9dbSNicholas Bellinger substring_t args[MAX_OPT_ARGS]; 53821bca31cSRoland Dreier int ret = 0, token; 53944bfd018SAndy Grover unsigned long tmp_readonly; 540c66ac9dbSNicholas Bellinger 541c66ac9dbSNicholas Bellinger opts = kstrdup(page, GFP_KERNEL); 542c66ac9dbSNicholas Bellinger if (!opts) 543c66ac9dbSNicholas Bellinger return -ENOMEM; 544c66ac9dbSNicholas Bellinger 545c66ac9dbSNicholas Bellinger orig = opts; 546c66ac9dbSNicholas Bellinger 54790c161b6SSebastian Andrzej Siewior while ((ptr = strsep(&opts, ",\n")) != NULL) { 548c66ac9dbSNicholas Bellinger if (!*ptr) 549c66ac9dbSNicholas Bellinger continue; 550c66ac9dbSNicholas Bellinger 551c66ac9dbSNicholas Bellinger token = match_token(ptr, tokens, args); 552c66ac9dbSNicholas Bellinger switch (token) { 553c66ac9dbSNicholas Bellinger case Opt_udev_path: 554c66ac9dbSNicholas Bellinger if (ib_dev->ibd_bd) { 5556708bb27SAndy Grover pr_err("Unable to set udev_path= while" 556c66ac9dbSNicholas Bellinger " ib_dev->ibd_bd exists\n"); 557c66ac9dbSNicholas Bellinger ret = -EEXIST; 558c66ac9dbSNicholas Bellinger goto out; 559c66ac9dbSNicholas Bellinger } 560852b6ed1SNicholas Bellinger if (match_strlcpy(ib_dev->ibd_udev_path, &args[0], 561852b6ed1SNicholas Bellinger SE_UDEV_PATH_LEN) == 0) { 562852b6ed1SNicholas Bellinger ret = -EINVAL; 5636d180253SJesper Juhl break; 5646d180253SJesper Juhl } 5656708bb27SAndy Grover pr_debug("IBLOCK: Referencing UDEV path: %s\n", 566c66ac9dbSNicholas Bellinger ib_dev->ibd_udev_path); 567c66ac9dbSNicholas Bellinger ib_dev->ibd_flags |= IBDF_HAS_UDEV_PATH; 568c66ac9dbSNicholas Bellinger break; 56944bfd018SAndy Grover case Opt_readonly: 57044bfd018SAndy Grover arg_p = match_strdup(&args[0]); 57144bfd018SAndy Grover if (!arg_p) { 57244bfd018SAndy Grover ret = -ENOMEM; 57344bfd018SAndy Grover break; 57444bfd018SAndy Grover } 57557103d7fSJingoo Han ret = kstrtoul(arg_p, 0, &tmp_readonly); 57644bfd018SAndy Grover kfree(arg_p); 57744bfd018SAndy Grover if (ret < 0) { 57857103d7fSJingoo Han pr_err("kstrtoul() failed for" 57944bfd018SAndy Grover " readonly=\n"); 58044bfd018SAndy Grover goto out; 58144bfd018SAndy Grover } 58244bfd018SAndy Grover ib_dev->ibd_readonly = tmp_readonly; 58344bfd018SAndy Grover pr_debug("IBLOCK: readonly: %d\n", ib_dev->ibd_readonly); 58444bfd018SAndy Grover break; 585c66ac9dbSNicholas Bellinger case Opt_force: 586c66ac9dbSNicholas Bellinger break; 587c66ac9dbSNicholas Bellinger default: 588c66ac9dbSNicholas Bellinger break; 589c66ac9dbSNicholas Bellinger } 590c66ac9dbSNicholas Bellinger } 591c66ac9dbSNicholas Bellinger 592c66ac9dbSNicholas Bellinger out: 593c66ac9dbSNicholas Bellinger kfree(orig); 594c66ac9dbSNicholas Bellinger return (!ret) ? count : ret; 595c66ac9dbSNicholas Bellinger } 596c66ac9dbSNicholas Bellinger 5970fd97ccfSChristoph Hellwig static ssize_t iblock_show_configfs_dev_params(struct se_device *dev, char *b) 598c66ac9dbSNicholas Bellinger { 5990fd97ccfSChristoph Hellwig struct iblock_dev *ib_dev = IBLOCK_DEV(dev); 6000fd97ccfSChristoph Hellwig struct block_device *bd = ib_dev->ibd_bd; 601c66ac9dbSNicholas Bellinger char buf[BDEVNAME_SIZE]; 602c66ac9dbSNicholas Bellinger ssize_t bl = 0; 603c66ac9dbSNicholas Bellinger 604c66ac9dbSNicholas Bellinger if (bd) 605c66ac9dbSNicholas Bellinger bl += sprintf(b + bl, "iBlock device: %s", 606c66ac9dbSNicholas Bellinger bdevname(bd, buf)); 6070fd97ccfSChristoph Hellwig if (ib_dev->ibd_flags & IBDF_HAS_UDEV_PATH) 60844bfd018SAndy Grover bl += sprintf(b + bl, " UDEV PATH: %s", 6090fd97ccfSChristoph Hellwig ib_dev->ibd_udev_path); 6100fd97ccfSChristoph Hellwig bl += sprintf(b + bl, " readonly: %d\n", ib_dev->ibd_readonly); 611c66ac9dbSNicholas Bellinger 612c66ac9dbSNicholas Bellinger bl += sprintf(b + bl, " "); 613c66ac9dbSNicholas Bellinger if (bd) { 614c66ac9dbSNicholas Bellinger bl += sprintf(b + bl, "Major: %d Minor: %d %s\n", 61521bca31cSRoland Dreier MAJOR(bd->bd_dev), MINOR(bd->bd_dev), (!bd->bd_contains) ? 6160fd97ccfSChristoph Hellwig "" : (bd->bd_holder == ib_dev) ? 617c66ac9dbSNicholas Bellinger "CLAIMED: IBLOCK" : "CLAIMED: OS"); 618c66ac9dbSNicholas Bellinger } else { 61921bca31cSRoland Dreier bl += sprintf(b + bl, "Major: 0 Minor: 0\n"); 620c66ac9dbSNicholas Bellinger } 621c66ac9dbSNicholas Bellinger 622c66ac9dbSNicholas Bellinger return bl; 623c66ac9dbSNicholas Bellinger } 624c66ac9dbSNicholas Bellinger 625ecebbf6cSNicholas Bellinger static int 626ecebbf6cSNicholas Bellinger iblock_alloc_bip(struct se_cmd *cmd, struct bio *bio) 627ecebbf6cSNicholas Bellinger { 628ecebbf6cSNicholas Bellinger struct se_device *dev = cmd->se_dev; 629ecebbf6cSNicholas Bellinger struct blk_integrity *bi; 630ecebbf6cSNicholas Bellinger struct bio_integrity_payload *bip; 631ecebbf6cSNicholas Bellinger struct iblock_dev *ib_dev = IBLOCK_DEV(dev); 632ecebbf6cSNicholas Bellinger struct scatterlist *sg; 633ecebbf6cSNicholas Bellinger int i, rc; 634ecebbf6cSNicholas Bellinger 635ecebbf6cSNicholas Bellinger bi = bdev_get_integrity(ib_dev->ibd_bd); 636ecebbf6cSNicholas Bellinger if (!bi) { 637ecebbf6cSNicholas Bellinger pr_err("Unable to locate bio_integrity\n"); 638ecebbf6cSNicholas Bellinger return -ENODEV; 639ecebbf6cSNicholas Bellinger } 640ecebbf6cSNicholas Bellinger 641ecebbf6cSNicholas Bellinger bip = bio_integrity_alloc(bio, GFP_NOIO, cmd->t_prot_nents); 64206c1e390SKeith Busch if (IS_ERR(bip)) { 643ecebbf6cSNicholas Bellinger pr_err("Unable to allocate bio_integrity_payload\n"); 64406c1e390SKeith Busch return PTR_ERR(bip); 645ecebbf6cSNicholas Bellinger } 646ecebbf6cSNicholas Bellinger 6474e13c5d0SLinus Torvalds bip->bip_iter.bi_size = (cmd->data_length / dev->dev_attrib.block_size) * 648ecebbf6cSNicholas Bellinger dev->prot_length; 6494e13c5d0SLinus Torvalds bip->bip_iter.bi_sector = bio->bi_iter.bi_sector; 650ecebbf6cSNicholas Bellinger 6514e13c5d0SLinus Torvalds pr_debug("IBLOCK BIP Size: %u Sector: %llu\n", bip->bip_iter.bi_size, 6524e13c5d0SLinus Torvalds (unsigned long long)bip->bip_iter.bi_sector); 653ecebbf6cSNicholas Bellinger 654ecebbf6cSNicholas Bellinger for_each_sg(cmd->t_prot_sg, sg, cmd->t_prot_nents, i) { 655ecebbf6cSNicholas Bellinger 656ecebbf6cSNicholas Bellinger rc = bio_integrity_add_page(bio, sg_page(sg), sg->length, 657ecebbf6cSNicholas Bellinger sg->offset); 658ecebbf6cSNicholas Bellinger if (rc != sg->length) { 659ecebbf6cSNicholas Bellinger pr_err("bio_integrity_add_page() failed; %d\n", rc); 660ecebbf6cSNicholas Bellinger return -ENOMEM; 661ecebbf6cSNicholas Bellinger } 662ecebbf6cSNicholas Bellinger 663ecebbf6cSNicholas Bellinger pr_debug("Added bio integrity page: %p length: %d offset; %d\n", 664ecebbf6cSNicholas Bellinger sg_page(sg), sg->length, sg->offset); 665ecebbf6cSNicholas Bellinger } 666ecebbf6cSNicholas Bellinger 667ecebbf6cSNicholas Bellinger return 0; 668ecebbf6cSNicholas Bellinger } 669ecebbf6cSNicholas Bellinger 670de103c93SChristoph Hellwig static sense_reason_t 671a82a9538SNicholas Bellinger iblock_execute_rw(struct se_cmd *cmd, struct scatterlist *sgl, u32 sgl_nents, 672a82a9538SNicholas Bellinger enum dma_data_direction data_direction) 673c66ac9dbSNicholas Bellinger { 6745951146dSAndy Grover struct se_device *dev = cmd->se_dev; 6758a9ebe71SMike Christie sector_t block_lba = target_to_linux_sector(dev, cmd->t_task_lba); 6765787cacdSChristoph Hellwig struct iblock_req *ibr; 677ecebbf6cSNicholas Bellinger struct bio *bio, *bio_start; 678dbbf3e94SChristoph Hellwig struct bio_list list; 679c66ac9dbSNicholas Bellinger struct scatterlist *sg; 6805787cacdSChristoph Hellwig u32 sg_num = sgl_nents; 681d5b4a21bSChristoph Hellwig unsigned bio_cnt; 682d0c8b259SNicholas Bellinger int rw = 0; 6835787cacdSChristoph Hellwig int i; 684dbbf3e94SChristoph Hellwig 6855787cacdSChristoph Hellwig if (data_direction == DMA_TO_DEVICE) { 686d0c8b259SNicholas Bellinger struct iblock_dev *ib_dev = IBLOCK_DEV(dev); 687d0c8b259SNicholas Bellinger struct request_queue *q = bdev_get_queue(ib_dev->ibd_bd); 688dbbf3e94SChristoph Hellwig /* 689d0c8b259SNicholas Bellinger * Force writethrough using WRITE_FUA if a volatile write cache 690d0c8b259SNicholas Bellinger * is not enabled, or if initiator set the Force Unit Access bit. 691dbbf3e94SChristoph Hellwig */ 692c888a8f9SJens Axboe if (test_bit(QUEUE_FLAG_FUA, &q->queue_flags)) { 693d0c8b259SNicholas Bellinger if (cmd->se_cmd_flags & SCF_FUA) 694dbbf3e94SChristoph Hellwig rw = WRITE_FUA; 695c888a8f9SJens Axboe else if (!test_bit(QUEUE_FLAG_WC, &q->queue_flags)) 696d0c8b259SNicholas Bellinger rw = WRITE_FUA; 697d2bdbee0SNicholas Bellinger else 698d2bdbee0SNicholas Bellinger rw = WRITE; 699d0c8b259SNicholas Bellinger } else { 700dbbf3e94SChristoph Hellwig rw = WRITE; 701d0c8b259SNicholas Bellinger } 702dbbf3e94SChristoph Hellwig } else { 703dbbf3e94SChristoph Hellwig rw = READ; 704dbbf3e94SChristoph Hellwig } 705dbbf3e94SChristoph Hellwig 7065787cacdSChristoph Hellwig ibr = kzalloc(sizeof(struct iblock_req), GFP_KERNEL); 7075787cacdSChristoph Hellwig if (!ibr) 7085787cacdSChristoph Hellwig goto fail; 7095787cacdSChristoph Hellwig cmd->priv = ibr; 7105787cacdSChristoph Hellwig 711e0de4457SPaolo Bonzini if (!sgl_nents) { 712e0de4457SPaolo Bonzini atomic_set(&ibr->pending, 1); 713e0de4457SPaolo Bonzini iblock_complete_cmd(cmd); 714e0de4457SPaolo Bonzini return 0; 715e0de4457SPaolo Bonzini } 716e0de4457SPaolo Bonzini 7174e49ea4aSMike Christie bio = iblock_get_bio(cmd, block_lba, sgl_nents, rw); 7185787cacdSChristoph Hellwig if (!bio) 7195787cacdSChristoph Hellwig goto fail_free_ibr; 720c66ac9dbSNicholas Bellinger 721ecebbf6cSNicholas Bellinger bio_start = bio; 722dbbf3e94SChristoph Hellwig bio_list_init(&list); 723dbbf3e94SChristoph Hellwig bio_list_add(&list, bio); 7245787cacdSChristoph Hellwig 7255787cacdSChristoph Hellwig atomic_set(&ibr->pending, 2); 726d5b4a21bSChristoph Hellwig bio_cnt = 1; 727dbbf3e94SChristoph Hellwig 7285787cacdSChristoph Hellwig for_each_sg(sgl, sg, sgl_nents, i) { 729dbbf3e94SChristoph Hellwig /* 730dbbf3e94SChristoph Hellwig * XXX: if the length the device accepts is shorter than the 731dbbf3e94SChristoph Hellwig * length of the S/G list entry this will cause and 732dbbf3e94SChristoph Hellwig * endless loop. Better hope no driver uses huge pages. 733dbbf3e94SChristoph Hellwig */ 734dbbf3e94SChristoph Hellwig while (bio_add_page(bio, sg_page(sg), sg->length, sg->offset) 735dbbf3e94SChristoph Hellwig != sg->length) { 736d5b4a21bSChristoph Hellwig if (bio_cnt >= IBLOCK_MAX_BIO_PER_TASK) { 7374e49ea4aSMike Christie iblock_submit_bios(&list); 738d5b4a21bSChristoph Hellwig bio_cnt = 0; 739d5b4a21bSChristoph Hellwig } 740d5b4a21bSChristoph Hellwig 7414e49ea4aSMike Christie bio = iblock_get_bio(cmd, block_lba, sg_num, rw); 7426708bb27SAndy Grover if (!bio) 7435787cacdSChristoph Hellwig goto fail_put_bios; 7445787cacdSChristoph Hellwig 7455787cacdSChristoph Hellwig atomic_inc(&ibr->pending); 746dbbf3e94SChristoph Hellwig bio_list_add(&list, bio); 747d5b4a21bSChristoph Hellwig bio_cnt++; 748c66ac9dbSNicholas Bellinger } 749dbbf3e94SChristoph Hellwig 750c66ac9dbSNicholas Bellinger /* Always in 512 byte units for Linux/Block */ 751c66ac9dbSNicholas Bellinger block_lba += sg->length >> IBLOCK_LBA_SHIFT; 752c66ac9dbSNicholas Bellinger sg_num--; 753c66ac9dbSNicholas Bellinger } 754c66ac9dbSNicholas Bellinger 7556f16ec43SNicholas Bellinger if (cmd->prot_type && dev->dev_attrib.pi_prot_type) { 756ecebbf6cSNicholas Bellinger int rc = iblock_alloc_bip(cmd, bio_start); 757ecebbf6cSNicholas Bellinger if (rc) 758ecebbf6cSNicholas Bellinger goto fail_put_bios; 759ecebbf6cSNicholas Bellinger } 760ecebbf6cSNicholas Bellinger 7614e49ea4aSMike Christie iblock_submit_bios(&list); 7625787cacdSChristoph Hellwig iblock_complete_cmd(cmd); 76303e98c9eSNicholas Bellinger return 0; 764dbbf3e94SChristoph Hellwig 7655787cacdSChristoph Hellwig fail_put_bios: 766dbbf3e94SChristoph Hellwig while ((bio = bio_list_pop(&list))) 767c66ac9dbSNicholas Bellinger bio_put(bio); 7685787cacdSChristoph Hellwig fail_free_ibr: 7695787cacdSChristoph Hellwig kfree(ibr); 7705787cacdSChristoph Hellwig fail: 771de103c93SChristoph Hellwig return TCM_LOGICAL_UNIT_COMMUNICATION_FAILURE; 772c66ac9dbSNicholas Bellinger } 773c66ac9dbSNicholas Bellinger 774c66ac9dbSNicholas Bellinger static sector_t iblock_get_blocks(struct se_device *dev) 775c66ac9dbSNicholas Bellinger { 7760fd97ccfSChristoph Hellwig struct iblock_dev *ib_dev = IBLOCK_DEV(dev); 7770fd97ccfSChristoph Hellwig struct block_device *bd = ib_dev->ibd_bd; 778c66ac9dbSNicholas Bellinger struct request_queue *q = bdev_get_queue(bd); 779c66ac9dbSNicholas Bellinger 780c66ac9dbSNicholas Bellinger return iblock_emulate_read_cap_with_block_size(dev, bd, q); 781c66ac9dbSNicholas Bellinger } 782c66ac9dbSNicholas Bellinger 7837f7caf6aSAndy Grover static sector_t iblock_get_alignment_offset_lbas(struct se_device *dev) 7847f7caf6aSAndy Grover { 7857f7caf6aSAndy Grover struct iblock_dev *ib_dev = IBLOCK_DEV(dev); 7867f7caf6aSAndy Grover struct block_device *bd = ib_dev->ibd_bd; 7877f7caf6aSAndy Grover int ret; 7887f7caf6aSAndy Grover 7897f7caf6aSAndy Grover ret = bdev_alignment_offset(bd); 7907f7caf6aSAndy Grover if (ret == -1) 7917f7caf6aSAndy Grover return 0; 7927f7caf6aSAndy Grover 7937f7caf6aSAndy Grover /* convert offset-bytes to offset-lbas */ 7947f7caf6aSAndy Grover return ret / bdev_logical_block_size(bd); 7957f7caf6aSAndy Grover } 7967f7caf6aSAndy Grover 7977f7caf6aSAndy Grover static unsigned int iblock_get_lbppbe(struct se_device *dev) 7987f7caf6aSAndy Grover { 7997f7caf6aSAndy Grover struct iblock_dev *ib_dev = IBLOCK_DEV(dev); 8007f7caf6aSAndy Grover struct block_device *bd = ib_dev->ibd_bd; 8017f7caf6aSAndy Grover int logs_per_phys = bdev_physical_block_size(bd) / bdev_logical_block_size(bd); 8027f7caf6aSAndy Grover 8037f7caf6aSAndy Grover return ilog2(logs_per_phys); 8047f7caf6aSAndy Grover } 8057f7caf6aSAndy Grover 8067f7caf6aSAndy Grover static unsigned int iblock_get_io_min(struct se_device *dev) 8077f7caf6aSAndy Grover { 8087f7caf6aSAndy Grover struct iblock_dev *ib_dev = IBLOCK_DEV(dev); 8097f7caf6aSAndy Grover struct block_device *bd = ib_dev->ibd_bd; 8107f7caf6aSAndy Grover 8117f7caf6aSAndy Grover return bdev_io_min(bd); 8127f7caf6aSAndy Grover } 8137f7caf6aSAndy Grover 8147f7caf6aSAndy Grover static unsigned int iblock_get_io_opt(struct se_device *dev) 8157f7caf6aSAndy Grover { 8167f7caf6aSAndy Grover struct iblock_dev *ib_dev = IBLOCK_DEV(dev); 8177f7caf6aSAndy Grover struct block_device *bd = ib_dev->ibd_bd; 8187f7caf6aSAndy Grover 8197f7caf6aSAndy Grover return bdev_io_opt(bd); 8207f7caf6aSAndy Grover } 8217f7caf6aSAndy Grover 8229e999a6cSChristoph Hellwig static struct sbc_ops iblock_sbc_ops = { 8230c2ad7d1SChristoph Hellwig .execute_rw = iblock_execute_rw, 824ad67f0d9SChristoph Hellwig .execute_sync_cache = iblock_execute_sync_cache, 8256f974e8cSChristoph Hellwig .execute_write_same = iblock_execute_write_same, 82614150a6bSChristoph Hellwig .execute_unmap = iblock_execute_unmap, 8270c2ad7d1SChristoph Hellwig }; 8280c2ad7d1SChristoph Hellwig 829de103c93SChristoph Hellwig static sense_reason_t 830de103c93SChristoph Hellwig iblock_parse_cdb(struct se_cmd *cmd) 8310c2ad7d1SChristoph Hellwig { 8329e999a6cSChristoph Hellwig return sbc_parse_cdb(cmd, &iblock_sbc_ops); 8330c2ad7d1SChristoph Hellwig } 8340c2ad7d1SChristoph Hellwig 835452e2010SRashika Kheria static bool iblock_get_write_cache(struct se_device *dev) 836d0c8b259SNicholas Bellinger { 837d0c8b259SNicholas Bellinger struct iblock_dev *ib_dev = IBLOCK_DEV(dev); 838d0c8b259SNicholas Bellinger struct block_device *bd = ib_dev->ibd_bd; 839d0c8b259SNicholas Bellinger struct request_queue *q = bdev_get_queue(bd); 840d0c8b259SNicholas Bellinger 841c888a8f9SJens Axboe return test_bit(QUEUE_FLAG_WC, &q->queue_flags); 842d0c8b259SNicholas Bellinger } 843d0c8b259SNicholas Bellinger 8440a06d430SChristoph Hellwig static const struct target_backend_ops iblock_ops = { 845c66ac9dbSNicholas Bellinger .name = "iblock", 8460fd97ccfSChristoph Hellwig .inquiry_prod = "IBLOCK", 8470fd97ccfSChristoph Hellwig .inquiry_rev = IBLOCK_VERSION, 848c66ac9dbSNicholas Bellinger .owner = THIS_MODULE, 849c66ac9dbSNicholas Bellinger .attach_hba = iblock_attach_hba, 850c66ac9dbSNicholas Bellinger .detach_hba = iblock_detach_hba, 8510fd97ccfSChristoph Hellwig .alloc_device = iblock_alloc_device, 8520fd97ccfSChristoph Hellwig .configure_device = iblock_configure_device, 853c66ac9dbSNicholas Bellinger .free_device = iblock_free_device, 8540c2ad7d1SChristoph Hellwig .parse_cdb = iblock_parse_cdb, 855c66ac9dbSNicholas Bellinger .set_configfs_dev_params = iblock_set_configfs_dev_params, 856c66ac9dbSNicholas Bellinger .show_configfs_dev_params = iblock_show_configfs_dev_params, 8576f23ac8aSChristoph Hellwig .get_device_type = sbc_get_device_type, 858c66ac9dbSNicholas Bellinger .get_blocks = iblock_get_blocks, 8597f7caf6aSAndy Grover .get_alignment_offset_lbas = iblock_get_alignment_offset_lbas, 8607f7caf6aSAndy Grover .get_lbppbe = iblock_get_lbppbe, 8617f7caf6aSAndy Grover .get_io_min = iblock_get_io_min, 8627f7caf6aSAndy Grover .get_io_opt = iblock_get_io_opt, 863d0c8b259SNicholas Bellinger .get_write_cache = iblock_get_write_cache, 8645873c4d1SChristoph Hellwig .tb_dev_attrib_attrs = sbc_attrib_attrs, 865c66ac9dbSNicholas Bellinger }; 866c66ac9dbSNicholas Bellinger 867c66ac9dbSNicholas Bellinger static int __init iblock_module_init(void) 868c66ac9dbSNicholas Bellinger { 8690a06d430SChristoph Hellwig return transport_backend_register(&iblock_ops); 870c66ac9dbSNicholas Bellinger } 871c66ac9dbSNicholas Bellinger 87263b91d5aSAsias He static void __exit iblock_module_exit(void) 873c66ac9dbSNicholas Bellinger { 8740a06d430SChristoph Hellwig target_backend_unregister(&iblock_ops); 875c66ac9dbSNicholas Bellinger } 876c66ac9dbSNicholas Bellinger 877c66ac9dbSNicholas Bellinger MODULE_DESCRIPTION("TCM IBLOCK subsystem plugin"); 878c66ac9dbSNicholas Bellinger MODULE_AUTHOR("nab@Linux-iSCSI.org"); 879c66ac9dbSNicholas Bellinger MODULE_LICENSE("GPL"); 880c66ac9dbSNicholas Bellinger 881c66ac9dbSNicholas Bellinger module_init(iblock_module_init); 882c66ac9dbSNicholas Bellinger module_exit(iblock_module_exit); 883