Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 324071
b: refs/heads/master
c: 0d804b2
h: refs/heads/master
i:
  324069: 519ca67
  324067: ca42ab1
  324063: 98448bf
v: v3
  • Loading branch information
Sebastian Ott authored and Martin Schwidefsky committed Sep 26, 2012
1 parent 653f6a2 commit 6d16d43
Show file tree
Hide file tree
Showing 6 changed files with 311 additions and 4 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: f30664e2c85c7804f07c636bbe99f35e0b2d4c76
refs/heads/master: 0d804b20735d974534abb422f723d404b779433a
7 changes: 7 additions & 0 deletions trunk/drivers/s390/block/Kconfig
Original file line number Diff line number Diff line change
Expand Up @@ -81,3 +81,10 @@ config SCM_BLOCK

To compile this driver as a module, choose M here: the
module will be called scm_block.

config SCM_BLOCK_CLUSTER_WRITE
def_bool y
prompt "SCM force cluster writes"
depends on SCM_BLOCK
help
Force writes to Storage Class Memory (SCM) to be in done in clusters.
3 changes: 3 additions & 0 deletions trunk/drivers/s390/block/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -19,4 +19,7 @@ obj-$(CONFIG_BLK_DEV_XPRAM) += xpram.o
obj-$(CONFIG_DCSSBLK) += dcssblk.o

scm_block-objs := scm_drv.o scm_blk.o
ifdef CONFIG_SCM_BLOCK_CLUSTER_WRITE
scm_block-objs += scm_blk_cluster.o
endif
obj-$(CONFIG_SCM_BLOCK) += scm_block.o
37 changes: 34 additions & 3 deletions trunk/drivers/s390/block/scm_blk.c
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ static void __scm_free_rq(struct scm_request *scmrq)

free_page((unsigned long) scmrq->aob);
free_page((unsigned long) scmrq->aidaw);
__scm_free_rq_cluster(scmrq);
kfree(aobrq);
}

Expand Down Expand Up @@ -70,6 +71,12 @@ static int __scm_alloc_rq(void)
__scm_free_rq(scmrq);
return -ENOMEM;
}

if (__scm_alloc_rq_cluster(scmrq)) {
__scm_free_rq(scmrq);
return -ENOMEM;
}

INIT_LIST_HEAD(&scmrq->list);
spin_lock_irq(&list_lock);
list_add(&scmrq->list, &inactive_requests);
Expand Down Expand Up @@ -170,6 +177,7 @@ static inline void scm_request_init(struct scm_blk_dev *bdev,
scmrq->bdev = bdev;
scmrq->retries = 4;
scmrq->error = 0;
scm_request_cluster_init(scmrq);
}

static void scm_ensure_queue_restart(struct scm_blk_dev *bdev)
Expand All @@ -181,17 +189,19 @@ static void scm_ensure_queue_restart(struct scm_blk_dev *bdev)
blk_delay_queue(bdev->rq, SCM_QUEUE_DELAY);
}

static void scm_request_requeue(struct scm_request *scmrq)
void scm_request_requeue(struct scm_request *scmrq)
{
struct scm_blk_dev *bdev = scmrq->bdev;

scm_release_cluster(scmrq);
blk_requeue_request(bdev->rq, scmrq->request);
scm_request_done(scmrq);
scm_ensure_queue_restart(bdev);
}

static void scm_request_finish(struct scm_request *scmrq)
void scm_request_finish(struct scm_request *scmrq)
{
scm_release_cluster(scmrq);
blk_end_request_all(scmrq->request, scmrq->error);
scm_request_done(scmrq);
}
Expand All @@ -215,6 +225,16 @@ static void scm_blk_request(struct request_queue *rq)
return;
}
scm_request_init(bdev, scmrq, req);
if (!scm_reserve_cluster(scmrq)) {
SCM_LOG(5, "cluster busy");
scm_request_done(scmrq);
return;
}
if (scm_need_cluster_request(scmrq)) {
blk_start_request(req);
scm_initiate_cluster_request(scmrq);
return;
}
scm_request_prepare(scmrq);
blk_start_request(req);

Expand Down Expand Up @@ -282,6 +302,13 @@ static void scm_blk_tasklet(struct scm_blk_dev *bdev)
spin_lock_irqsave(&bdev->lock, flags);
continue;
}

if (scm_test_cluster_request(scmrq)) {
scm_cluster_request_irq(scmrq);
spin_lock_irqsave(&bdev->lock, flags);
continue;
}

scm_request_finish(scmrq);
atomic_dec(&bdev->queued_reqs);
spin_lock_irqsave(&bdev->lock, flags);
Expand Down Expand Up @@ -325,6 +352,7 @@ int scm_blk_dev_setup(struct scm_blk_dev *bdev, struct scm_device *scmdev)
blk_queue_max_hw_sectors(rq, nr_max_blk << 3); /* 8 * 512 = blk_size */
blk_queue_max_segments(rq, nr_max_blk);
queue_flag_set_unlocked(QUEUE_FLAG_NONROT, rq);
scm_blk_dev_cluster_setup(bdev);

bdev->gendisk = alloc_disk(SCM_NR_PARTS);
if (!bdev->gendisk)
Expand Down Expand Up @@ -370,7 +398,10 @@ void scm_blk_dev_cleanup(struct scm_blk_dev *bdev)

static int __init scm_blk_init(void)
{
int ret;
int ret = -EINVAL;

if (!scm_cluster_size_valid())
goto out;

ret = register_blkdev(0, "scm");
if (ret < 0)
Expand Down
38 changes: 38 additions & 0 deletions trunk/drivers/s390/block/scm_blk.h
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,9 @@ struct scm_blk_dev {
spinlock_t lock; /* guard the rest of the blockdev */
atomic_t queued_reqs;
struct list_head finished_requests;
#ifdef CONFIG_SCM_BLOCK_CLUSTER_WRITE
struct list_head cluster_list;
#endif
};

struct scm_request {
Expand All @@ -32,6 +35,13 @@ struct scm_request {
struct list_head list;
u8 retries;
int error;
#ifdef CONFIG_SCM_BLOCK_CLUSTER_WRITE
struct {
enum {CLUSTER_NONE, CLUSTER_READ, CLUSTER_WRITE} state;
struct list_head list;
void **buf;
} cluster;
#endif
};

#define to_aobrq(rq) container_of((void *) rq, struct aob_rq_header, data)
Expand All @@ -40,9 +50,37 @@ int scm_blk_dev_setup(struct scm_blk_dev *, struct scm_device *);
void scm_blk_dev_cleanup(struct scm_blk_dev *);
void scm_blk_irq(struct scm_device *, void *, int);

void scm_request_finish(struct scm_request *);
void scm_request_requeue(struct scm_request *);

int scm_drv_init(void);
void scm_drv_cleanup(void);

#ifdef CONFIG_SCM_BLOCK_CLUSTER_WRITE
void __scm_free_rq_cluster(struct scm_request *);
int __scm_alloc_rq_cluster(struct scm_request *);
void scm_request_cluster_init(struct scm_request *);
bool scm_reserve_cluster(struct scm_request *);
void scm_release_cluster(struct scm_request *);
void scm_blk_dev_cluster_setup(struct scm_blk_dev *);
bool scm_need_cluster_request(struct scm_request *);
void scm_initiate_cluster_request(struct scm_request *);
void scm_cluster_request_irq(struct scm_request *);
bool scm_test_cluster_request(struct scm_request *);
bool scm_cluster_size_valid(void);
#else
#define __scm_free_rq_cluster(scmrq) {}
#define __scm_alloc_rq_cluster(scmrq) 0
#define scm_request_cluster_init(scmrq) {}
#define scm_reserve_cluster(scmrq) true
#define scm_release_cluster(scmrq) {}
#define scm_blk_dev_cluster_setup(bdev) {}
#define scm_need_cluster_request(scmrq) false
#define scm_initiate_cluster_request(scmrq) {}
#define scm_cluster_request_irq(scmrq) {}
#define scm_test_cluster_request(scmrq) false
#define scm_cluster_size_valid() true
#endif

extern debug_info_t *scm_debug;

Expand Down
Loading

0 comments on commit 6d16d43

Please sign in to comment.