Changeset View
Changeset View
Standalone View
Standalone View
sys/dev/nvd/nvd.c
Show First 20 Lines • Show All 59 Lines • ▼ Show 20 Lines | |||||
static disk_getattr_t nvd_getattr; | static disk_getattr_t nvd_getattr; | ||||
static void nvd_done(void *arg, const struct nvme_completion *cpl); | static void nvd_done(void *arg, const struct nvme_completion *cpl); | ||||
static void nvd_gone(struct nvd_disk *ndisk); | static void nvd_gone(struct nvd_disk *ndisk); | ||||
static void *nvd_new_disk(struct nvme_namespace *ns, void *ctrlr); | static void *nvd_new_disk(struct nvme_namespace *ns, void *ctrlr); | ||||
static void *nvd_new_controller(struct nvme_controller *ctrlr); | static void *nvd_new_controller(struct nvme_controller *ctrlr); | ||||
static void nvd_controller_async(void *ctrlr_arg, | |||||
const struct nvme_completion *async_cpl, | |||||
uint32_t log_page_id, void *log_page_buffer, uint32_t log_page_size); | |||||
static void nvd_controller_fail(void *ctrlr); | static void nvd_controller_fail(void *ctrlr); | ||||
static int nvd_load(void); | static int nvd_load(void); | ||||
static void nvd_unload(void); | static void nvd_unload(void); | ||||
MALLOC_DEFINE(M_NVD, "nvd", "nvd(4) allocations"); | MALLOC_DEFINE(M_NVD, "nvd", "nvd(4) allocations"); | ||||
struct nvme_consumer *consumer_handle; | struct nvme_consumer *consumer_handle; | ||||
▲ Show 20 Lines • Show All 76 Lines • ▼ Show 20 Lines | nvd_load() | ||||
if (!nvme_use_nvd) | if (!nvme_use_nvd) | ||||
return 0; | return 0; | ||||
mtx_init(&nvd_lock, "nvd_lock", NULL, MTX_DEF); | mtx_init(&nvd_lock, "nvd_lock", NULL, MTX_DEF); | ||||
TAILQ_INIT(&ctrlr_head); | TAILQ_INIT(&ctrlr_head); | ||||
TAILQ_INIT(&disk_head); | TAILQ_INIT(&disk_head); | ||||
consumer_handle = nvme_register_consumer(nvd_new_disk, | consumer_handle = nvme_register_consumer(nvd_new_disk, | ||||
nvd_new_controller, NULL, nvd_controller_fail); | nvd_new_controller, nvd_controller_async, nvd_controller_fail); | ||||
return (consumer_handle != NULL ? 0 : -1); | return (consumer_handle != NULL ? 0 : -1); | ||||
} | } | ||||
static void | static void | ||||
nvd_unload() | nvd_unload() | ||||
{ | { | ||||
struct nvd_controller *ctrlr; | struct nvd_controller *ctrlr; | ||||
▲ Show 20 Lines • Show All 91 Lines • ▼ Show 20 Lines | while ((bp = bioq_takefirst(&ndisk->bioq)) != NULL) { | ||||
bp->bio_flags |= BIO_ERROR; | bp->bio_flags |= BIO_ERROR; | ||||
bp->bio_resid = bp->bio_bcount; | bp->bio_resid = bp->bio_bcount; | ||||
biodone(bp); | biodone(bp); | ||||
} | } | ||||
mtx_unlock(&ndisk->bioqlock); | mtx_unlock(&ndisk->bioqlock); | ||||
} | } | ||||
static void | static void | ||||
nvd_resize(struct nvd_disk *ndisk) | |||||
{ | |||||
struct disk *disk = ndisk->disk; | |||||
struct nvme_namespace *ns = ndisk->ns; | |||||
disk->d_sectorsize = nvme_ns_get_sector_size(ns); | |||||
disk->d_mediasize = (off_t)nvme_ns_get_size(ns); | |||||
disk->d_maxsize = nvme_ns_get_max_io_xfer_size(ns); | |||||
disk->d_delmaxsize = (off_t)nvme_ns_get_size(ns); | |||||
if (disk->d_delmaxsize > nvd_delete_max) | |||||
disk->d_delmaxsize = nvd_delete_max; | |||||
disk_resize(disk, M_NOWAIT); | |||||
printf(NVD_STR"%u: NVMe namespace resized\n", ndisk->unit); | |||||
printf(NVD_STR"%u: %juMB (%ju %u byte sectors)\n", disk->d_unit, | |||||
(uintmax_t)disk->d_mediasize / (1024*1024), | |||||
(uintmax_t)disk->d_mediasize / disk->d_sectorsize, | |||||
disk->d_sectorsize); | |||||
} | |||||
static void | |||||
nvd_gonecb(struct disk *dp) | nvd_gonecb(struct disk *dp) | ||||
{ | { | ||||
struct nvd_disk *ndisk = (struct nvd_disk *)dp->d_drv1; | struct nvd_disk *ndisk = (struct nvd_disk *)dp->d_drv1; | ||||
disk_destroy(ndisk->disk); | disk_destroy(ndisk->disk); | ||||
mtx_lock(&nvd_lock); | mtx_lock(&nvd_lock); | ||||
TAILQ_REMOVE(&disk_head, ndisk, global_tailq); | TAILQ_REMOVE(&disk_head, ndisk, global_tailq); | ||||
TAILQ_REMOVE(&ndisk->ctrlr->disk_head, ndisk, ctrlr_tailq); | TAILQ_REMOVE(&ndisk->ctrlr->disk_head, ndisk, ctrlr_tailq); | ||||
▲ Show 20 Lines • Show All 220 Lines • ▼ Show 20 Lines | nvd_new_disk(struct nvme_namespace *ns, void *ctrlr_arg) | ||||
printf(NVD_STR"%u: <%s> NVMe namespace\n", disk->d_unit, descr); | printf(NVD_STR"%u: <%s> NVMe namespace\n", disk->d_unit, descr); | ||||
printf(NVD_STR"%u: %juMB (%ju %u byte sectors)\n", disk->d_unit, | printf(NVD_STR"%u: %juMB (%ju %u byte sectors)\n", disk->d_unit, | ||||
(uintmax_t)disk->d_mediasize / (1024*1024), | (uintmax_t)disk->d_mediasize / (1024*1024), | ||||
(uintmax_t)disk->d_mediasize / disk->d_sectorsize, | (uintmax_t)disk->d_mediasize / disk->d_sectorsize, | ||||
disk->d_sectorsize); | disk->d_sectorsize); | ||||
return (ndisk); | return (ndisk); | ||||
} | |||||
static void | |||||
nvd_controller_async(void *ctrlr_arg, const struct nvme_completion *async_cpl, | |||||
uint32_t log_page_id, void *log_page_buffer, uint32_t log_page_size) | |||||
{ | |||||
struct nvd_controller *ctrlr = ctrlr_arg; | |||||
struct nvd_disk *ndisk; | |||||
mtx_lock(&nvd_lock); | |||||
TAILQ_FOREACH(ndisk, &ctrlr->disk_head, ctrlr_tailq) | |||||
nvd_resize(ndisk); | |||||
mtx_unlock(&nvd_lock); | |||||
} | } | ||||
static void | static void | ||||
nvd_controller_fail(void *ctrlr_arg) | nvd_controller_fail(void *ctrlr_arg) | ||||
{ | { | ||||
struct nvd_controller *ctrlr = ctrlr_arg; | struct nvd_controller *ctrlr = ctrlr_arg; | ||||
struct nvd_disk *ndisk; | struct nvd_disk *ndisk; | ||||
Show All 9 Lines |