svn commit: r352798 - in head/sys: dev/nvdimm modules/nvdimm

Conrad Meyer cem at FreeBSD.org
Fri Sep 27 16:32:45 UTC 2019


Author: cem
Date: Fri Sep 27 16:32:44 2019
New Revision: 352798
URL: https://svnweb.freebsd.org/changeset/base/352798

Log:
  nvdimm(4): Extract ACPI root bus driver
  
  No functional change intended.
  
  The intent is to add a "legacy" e820 pmem newbus bus for nvdimm device in a
  subsequent revision, and it's a little more clear if the parent buses get
  independent source files.
  
  Quite a lot of ACPI-specific logic is left in nvdimm.c; disentangling that
  is a much larger change (and probably not especially useful).
  
  Reviewed by:	kib
  Sponsored by:	Dell EMC Isilon
  Differential Revision:	https://reviews.freebsd.org/D21813

Added:
  head/sys/dev/nvdimm/nvdimm_acpi.c
     - copied, changed from r352792, head/sys/dev/nvdimm/nvdimm.c
Modified:
  head/sys/dev/nvdimm/nvdimm.c
  head/sys/dev/nvdimm/nvdimm_var.h
  head/sys/modules/nvdimm/Makefile

Modified: head/sys/dev/nvdimm/nvdimm.c
==============================================================================
--- head/sys/dev/nvdimm/nvdimm.c	Fri Sep 27 16:27:52 2019	(r352797)
+++ head/sys/dev/nvdimm/nvdimm.c	Fri Sep 27 16:32:44 2019	(r352798)
@@ -43,10 +43,12 @@ __FBSDID("$FreeBSD$");
 #include <sys/malloc.h>
 #include <sys/module.h>
 #include <sys/uuid.h>
+
 #include <contrib/dev/acpica/include/acpi.h>
 #include <contrib/dev/acpica/include/accommon.h>
 #include <contrib/dev/acpica/include/acuuid.h>
 #include <dev/acpica/acpivar.h>
+
 #include <dev/nvdimm/nvdimm_var.h>
 
 #define _COMPONENT	ACPI_OEM
@@ -59,7 +61,6 @@ static struct uuid intel_nvdimm_dsm_uuid =
 #define INTEL_NVDIMM_DSM_GET_LABEL_DATA 5
 
 static devclass_t nvdimm_devclass;
-static devclass_t nvdimm_root_devclass;
 MALLOC_DEFINE(M_NVDIMM, "nvdimm", "NVDIMM driver memory");
 
 static int
@@ -325,8 +326,7 @@ nvdimm_attach(device_t dev)
 
 	nv = device_get_softc(dev);
 	handle = nvdimm_root_get_acpi_handle(dev);
-	if (handle == NULL)
-		return (EINVAL);
+	MPASS(handle != NULL);
 	nv->nv_dev = dev;
 	nv->nv_handle = nvdimm_root_get_device_handle(dev);
 
@@ -380,204 +380,6 @@ nvdimm_resume(device_t dev)
 	return (0);
 }
 
-static ACPI_STATUS
-find_dimm(ACPI_HANDLE handle, UINT32 nesting_level, void *context,
-    void **return_value)
-{
-	ACPI_DEVICE_INFO *device_info;
-	ACPI_STATUS status;
-
-	status = AcpiGetObjectInfo(handle, &device_info);
-	if (ACPI_FAILURE(status))
-		return_ACPI_STATUS(AE_ERROR);
-	if (device_info->Address == (uintptr_t)context) {
-		*(ACPI_HANDLE *)return_value = handle;
-		return_ACPI_STATUS(AE_CTRL_TERMINATE);
-	}
-	return_ACPI_STATUS(AE_OK);
-}
-
-static ACPI_HANDLE
-get_dimm_acpi_handle(ACPI_HANDLE root_handle, nfit_handle_t adr)
-{
-	ACPI_HANDLE res;
-	ACPI_STATUS status;
-
-	res = NULL;
-	status = AcpiWalkNamespace(ACPI_TYPE_DEVICE, root_handle, 1, find_dimm,
-	    NULL, (void *)(uintptr_t)adr, &res);
-	if (ACPI_FAILURE(status))
-		res = NULL;
-	return (res);
-}
-
-static int
-nvdimm_root_create_devs(device_t dev, ACPI_TABLE_NFIT *nfitbl)
-{
-	ACPI_HANDLE root_handle, dimm_handle;
-	device_t child;
-	nfit_handle_t *dimm_ids, *dimm;
-	uintptr_t *ivars;
-	int num_dimm_ids;
-
-	root_handle = acpi_get_handle(dev);
-	acpi_nfit_get_dimm_ids(nfitbl, &dimm_ids, &num_dimm_ids);
-	for (dimm = dimm_ids; dimm < dimm_ids + num_dimm_ids; dimm++) {
-		dimm_handle = get_dimm_acpi_handle(root_handle, *dimm);
-		child = BUS_ADD_CHILD(dev, 100, "nvdimm", -1);
-		if (child == NULL) {
-			device_printf(dev, "failed to create nvdimm\n");
-			return (ENXIO);
-		}
-		ivars = mallocarray(NVDIMM_ROOT_IVAR_MAX, sizeof(uintptr_t),
-		    M_NVDIMM, M_ZERO | M_WAITOK);
-		device_set_ivars(child, ivars);
-		nvdimm_root_set_acpi_handle(child, dimm_handle);
-		nvdimm_root_set_device_handle(child, *dimm);
-	}
-	free(dimm_ids, M_NVDIMM);
-	return (0);
-}
-
-static int
-nvdimm_root_create_spas(struct nvdimm_root_dev *dev, ACPI_TABLE_NFIT *nfitbl)
-{
-	ACPI_NFIT_SYSTEM_ADDRESS **spas, **spa;
-	struct SPA_mapping *spa_mapping;
-	enum SPA_mapping_type spa_type;
-	int error, num_spas;
-
-	error = 0;
-	acpi_nfit_get_spa_ranges(nfitbl, &spas, &num_spas);
-	for (spa = spas; spa < spas + num_spas; spa++) {
-		spa_type = nvdimm_spa_type_from_uuid(
-			(struct uuid *)(*spa)->RangeGuid);
-		if (spa_type == SPA_TYPE_UNKNOWN)
-			continue;
-		spa_mapping = malloc(sizeof(struct SPA_mapping), M_NVDIMM,
-		    M_WAITOK | M_ZERO);
-		error = nvdimm_spa_init(spa_mapping, *spa, spa_type);
-		if (error != 0) {
-			nvdimm_spa_fini(spa_mapping);
-			free(spa, M_NVDIMM);
-			break;
-		}
-		nvdimm_create_namespaces(spa_mapping, nfitbl);
-		SLIST_INSERT_HEAD(&dev->spas, spa_mapping, link);
-	}
-	free(spas, M_NVDIMM);
-	return (error);
-}
-
-static char *nvdimm_root_id[] = {"ACPI0012", NULL};
-
-static int
-nvdimm_root_probe(device_t dev)
-{
-	int rv;
-
-	if (acpi_disabled("nvdimm"))
-		return (ENXIO);
-	rv = ACPI_ID_PROBE(device_get_parent(dev), dev, nvdimm_root_id, NULL);
-	if (rv <= 0)
-		device_set_desc(dev, "ACPI NVDIMM root device");
-
-	return (rv);
-}
-
-static int
-nvdimm_root_attach(device_t dev)
-{
-	struct nvdimm_root_dev *root;
-	ACPI_TABLE_NFIT *nfitbl;
-	ACPI_STATUS status;
-	int error;
-
-	status = AcpiGetTable(ACPI_SIG_NFIT, 1, (ACPI_TABLE_HEADER **)&nfitbl);
-	if (ACPI_FAILURE(status)) {
-		device_printf(dev, "cannot get NFIT\n");
-		return (ENXIO);
-	}
-	error = nvdimm_root_create_devs(dev, nfitbl);
-	if (error != 0)
-		return (error);
-	error = bus_generic_attach(dev);
-	if (error != 0)
-		return (error);
-	root = device_get_softc(dev);
-	error = nvdimm_root_create_spas(root, nfitbl);
-	AcpiPutTable(&nfitbl->Header);
-	return (error);
-}
-
-static int
-nvdimm_root_detach(device_t dev)
-{
-	struct nvdimm_root_dev *root;
-	struct SPA_mapping *spa, *next;
-	device_t *children;
-	int i, error, num_children;
-
-	root = device_get_softc(dev);
-	SLIST_FOREACH_SAFE(spa, &root->spas, link, next) {
-		nvdimm_destroy_namespaces(spa);
-		nvdimm_spa_fini(spa);
-		SLIST_REMOVE_HEAD(&root->spas, link);
-		free(spa, M_NVDIMM);
-	}
-	error = bus_generic_detach(dev);
-	if (error != 0)
-		return (error);
-	error = device_get_children(dev, &children, &num_children);
-	if (error != 0)
-		return (error);
-	for (i = 0; i < num_children; i++)
-		free(device_get_ivars(children[i]), M_NVDIMM);
-	free(children, M_TEMP);
-	error = device_delete_children(dev);
-	return (error);
-}
-
-static int
-nvdimm_root_read_ivar(device_t dev, device_t child, int index,
-    uintptr_t *result)
-{
-
-	if (index < 0 || index >= NVDIMM_ROOT_IVAR_MAX)
-		return (ENOENT);
-	*result = ((uintptr_t *)device_get_ivars(child))[index];
-	return (0);
-}
-
-static int
-nvdimm_root_write_ivar(device_t dev, device_t child, int index,
-    uintptr_t value)
-{
-
-	if (index < 0 || index >= NVDIMM_ROOT_IVAR_MAX)
-		return (ENOENT);
-	((uintptr_t *)device_get_ivars(child))[index] = value;
-	return (0);
-}
-
-static int
-nvdimm_root_child_location_str(device_t dev, device_t child, char *buf,
-    size_t buflen)
-{
-	ACPI_HANDLE handle;
-	int res;
-
-	handle = nvdimm_root_get_acpi_handle(child);
-	if (handle != NULL)
-		res = snprintf(buf, buflen, "handle=%s", acpi_name(handle));
-	else
-		res = snprintf(buf, buflen, "");
-
-	if (res >= buflen)
-		return (EOVERFLOW);
-	return (0);
-}
-
 static device_method_t nvdimm_methods[] = {
 	DEVMETHOD(device_probe, nvdimm_probe),
 	DEVMETHOD(device_attach, nvdimm_attach),
@@ -593,24 +395,6 @@ static driver_t	nvdimm_driver = {
 	sizeof(struct nvdimm_dev),
 };
 
-static device_method_t nvdimm_root_methods[] = {
-	DEVMETHOD(device_probe, nvdimm_root_probe),
-	DEVMETHOD(device_attach, nvdimm_root_attach),
-	DEVMETHOD(device_detach, nvdimm_root_detach),
-	DEVMETHOD(bus_add_child, bus_generic_add_child),
-	DEVMETHOD(bus_read_ivar, nvdimm_root_read_ivar),
-	DEVMETHOD(bus_write_ivar, nvdimm_root_write_ivar),
-	DEVMETHOD(bus_child_location_str, nvdimm_root_child_location_str),
-	DEVMETHOD_END
-};
-
-static driver_t	nvdimm_root_driver = {
-	"nvdimm_root",
-	nvdimm_root_methods,
-	sizeof(struct nvdimm_root_dev),
-};
-
-DRIVER_MODULE(nvdimm_root, acpi, nvdimm_root_driver, nvdimm_root_devclass, NULL,
+DRIVER_MODULE(nvdimm, nvdimm_acpi_root, nvdimm_driver, nvdimm_devclass, NULL,
     NULL);
-DRIVER_MODULE(nvdimm, nvdimm_root, nvdimm_driver, nvdimm_devclass, NULL, NULL);
 MODULE_DEPEND(nvdimm, acpi, 1, 1, 1);

Copied and modified: head/sys/dev/nvdimm/nvdimm_acpi.c (from r352792, head/sys/dev/nvdimm/nvdimm.c)
==============================================================================
--- head/sys/dev/nvdimm/nvdimm.c	Fri Sep 27 13:14:36 2019	(r352792, copy source)
+++ head/sys/dev/nvdimm/nvdimm_acpi.c	Fri Sep 27 16:32:44 2019	(r352798)
@@ -1,6 +1,5 @@
 /*-
  * Copyright (c) 2017 The FreeBSD Foundation
- * All rights reserved.
  * Copyright (c) 2018, 2019 Intel Corporation
  *
  * This software was developed by Konstantin Belousov <kib at FreeBSD.org>
@@ -43,343 +42,23 @@ __FBSDID("$FreeBSD$");
 #include <sys/malloc.h>
 #include <sys/module.h>
 #include <sys/uuid.h>
+
 #include <contrib/dev/acpica/include/acpi.h>
 #include <contrib/dev/acpica/include/accommon.h>
 #include <contrib/dev/acpica/include/acuuid.h>
 #include <dev/acpica/acpivar.h>
+
 #include <dev/nvdimm/nvdimm_var.h>
 
 #define _COMPONENT	ACPI_OEM
-ACPI_MODULE_NAME("NVDIMM")
+ACPI_MODULE_NAME("NVDIMM_ACPI")
 
-static struct uuid intel_nvdimm_dsm_uuid =
-    {0x4309AC30,0x0D11,0x11E4,0x91,0x91,{0x08,0x00,0x20,0x0C,0x9A,0x66}};
-#define INTEL_NVDIMM_DSM_REV 1
-#define INTEL_NVDIMM_DSM_GET_LABEL_SIZE 4
-#define INTEL_NVDIMM_DSM_GET_LABEL_DATA 5
+struct nvdimm_root_dev {
+	SLIST_HEAD(, SPA_mapping) spas;
+};
 
-static devclass_t nvdimm_devclass;
-static devclass_t nvdimm_root_devclass;
-MALLOC_DEFINE(M_NVDIMM, "nvdimm", "NVDIMM driver memory");
+static MALLOC_DEFINE(M_NVDIMM_ACPI, "nvdimm_acpi", "NVDIMM ACPI bus memory");
 
-static int
-read_label_area_size(struct nvdimm_dev *nv)
-{
-	ACPI_OBJECT *result_buffer;
-	ACPI_HANDLE handle;
-	ACPI_STATUS status;
-	ACPI_BUFFER result;
-	uint32_t *out;
-	int error;
-
-	handle = nvdimm_root_get_acpi_handle(nv->nv_dev);
-	if (handle == NULL)
-		return (ENODEV);
-	result.Length = ACPI_ALLOCATE_BUFFER;
-	result.Pointer = NULL;
-	status = acpi_EvaluateDSM(handle, (uint8_t *)&intel_nvdimm_dsm_uuid,
-	    INTEL_NVDIMM_DSM_REV, INTEL_NVDIMM_DSM_GET_LABEL_SIZE, NULL,
-	    &result);
-	error = ENXIO;
-	if (ACPI_SUCCESS(status) && result.Pointer != NULL &&
-	    result.Length >= sizeof(ACPI_OBJECT)) {
-		result_buffer = result.Pointer;
-		if (result_buffer->Type == ACPI_TYPE_BUFFER &&
-		    result_buffer->Buffer.Length >= 12) {
-			out = (uint32_t *)result_buffer->Buffer.Pointer;
-			nv->label_area_size = out[1];
-			nv->max_label_xfer = out[2];
-			error = 0;
-		}
-	}
-	if (result.Pointer != NULL)
-		AcpiOsFree(result.Pointer);
-	return (error);
-}
-
-static int
-read_label_area(struct nvdimm_dev *nv, uint8_t *dest, off_t offset,
-    off_t length)
-{
-	ACPI_BUFFER result;
-	ACPI_HANDLE handle;
-	ACPI_OBJECT params_pkg, params_buf, *result_buf;
-	ACPI_STATUS status;
-	uint32_t params[2];
-	off_t to_read;
-	int error;
-
-	error = 0;
-	handle = nvdimm_root_get_acpi_handle(nv->nv_dev);
-	if (offset < 0 || length <= 0 ||
-	    offset + length > nv->label_area_size ||
-	    handle == NULL)
-		return (ENODEV);
-	params_pkg.Type = ACPI_TYPE_PACKAGE;
-	params_pkg.Package.Count = 1;
-	params_pkg.Package.Elements = &params_buf;
-	params_buf.Type = ACPI_TYPE_BUFFER;
-	params_buf.Buffer.Length = sizeof(params);
-	params_buf.Buffer.Pointer = (UINT8 *)params;
-	while (length > 0) {
-		to_read = MIN(length, nv->max_label_xfer);
-		params[0] = offset;
-		params[1] = to_read;
-		result.Length = ACPI_ALLOCATE_BUFFER;
-		result.Pointer = NULL;
-		status = acpi_EvaluateDSM(handle,
-		    (uint8_t *)&intel_nvdimm_dsm_uuid, INTEL_NVDIMM_DSM_REV,
-		    INTEL_NVDIMM_DSM_GET_LABEL_DATA, &params_pkg, &result);
-		if (ACPI_FAILURE(status) ||
-		    result.Length < sizeof(ACPI_OBJECT) ||
-		    result.Pointer == NULL) {
-			error = ENXIO;
-			break;
-		}
-		result_buf = (ACPI_OBJECT *)result.Pointer;
-		if (result_buf->Type != ACPI_TYPE_BUFFER ||
-		    result_buf->Buffer.Pointer == NULL ||
-		    result_buf->Buffer.Length != 4 + to_read ||
-		    ((uint16_t *)result_buf->Buffer.Pointer)[0] != 0) {
-			error = ENXIO;
-			break;
-		}
-		bcopy(result_buf->Buffer.Pointer + 4, dest, to_read);
-		dest += to_read;
-		offset += to_read;
-		length -= to_read;
-		if (result.Pointer != NULL) {
-			AcpiOsFree(result.Pointer);
-			result.Pointer = NULL;
-		}
-	}
-	if (result.Pointer != NULL)
-		AcpiOsFree(result.Pointer);
-	return (error);
-}
-
-static uint64_t
-fletcher64(const void *data, size_t length)
-{
-	size_t i;
-	uint32_t a, b;
-	const uint32_t *d;
-
-	a = 0;
-	b = 0;
-	d = (const uint32_t *)data;
-	length = length / sizeof(uint32_t);
-	for (i = 0; i < length; i++) {
-		a += d[i];
-		b += a;
-	}
-	return ((uint64_t)b << 32 | a);
-}
-
-static bool
-label_index_is_valid(struct nvdimm_label_index *index, uint32_t max_labels,
-    size_t size, size_t offset)
-{
-	uint64_t checksum;
-
-	index = (struct nvdimm_label_index *)((uint8_t *)index + offset);
-	if (strcmp(index->signature, NVDIMM_INDEX_BLOCK_SIGNATURE) != 0)
-		return false;
-	checksum = index->checksum;
-	index->checksum = 0;
-	if (checksum != fletcher64(index, size) ||
-	    index->this_offset != size * offset || index->this_size != size ||
-	    index->other_offset != size * (offset == 0 ? 1 : 0) ||
-	    index->seq == 0 || index->seq > 3 || index->slot_cnt > max_labels ||
-	    index->label_size != 1)
-		return false;
-	return true;
-}
-
-static int
-read_label(struct nvdimm_dev *nv, int num)
-{
-	struct nvdimm_label_entry *entry, *i, *next;
-	uint64_t checksum;
-	off_t offset;
-	int error;
-
-	offset = nv->label_index->label_offset +
-	    num * (128 << nv->label_index->label_size);
-	entry = malloc(sizeof(*entry), M_NVDIMM, M_WAITOK);
-	error = read_label_area(nv, (uint8_t *)&entry->label, offset,
-	    sizeof(struct nvdimm_label));
-	if (error != 0) {
-		free(entry, M_NVDIMM);
-		return (error);
-	}
-	checksum = entry->label.checksum;
-	entry->label.checksum = 0;
-	if (checksum != fletcher64(&entry->label, sizeof(entry->label)) ||
-	    entry->label.slot != num) {
-		free(entry, M_NVDIMM);
-		return (ENXIO);
-	}
-
-	/* Insertion ordered by dimm_phys_addr */
-	if (SLIST_EMPTY(&nv->labels) ||
-	    entry->label.dimm_phys_addr <=
-	    SLIST_FIRST(&nv->labels)->label.dimm_phys_addr) {
-		SLIST_INSERT_HEAD(&nv->labels, entry, link);
-		return (0);
-	}
-	SLIST_FOREACH_SAFE(i, &nv->labels, link, next) {
-		if (next == NULL ||
-		    entry->label.dimm_phys_addr <= next->label.dimm_phys_addr) {
-			SLIST_INSERT_AFTER(i, entry, link);
-			return (0);
-		}
-	}
-	__unreachable();
-}
-
-static int
-read_labels(struct nvdimm_dev *nv)
-{
-	struct nvdimm_label_index *indices;
-	size_t bitfield_size, index_size, num_labels;
-	int error, n;
-	bool index_0_valid, index_1_valid;
-
-	for (index_size = 256; ; index_size += 256) {
-		num_labels = 8 * (index_size -
-		    sizeof(struct nvdimm_label_index));
-		if (index_size + num_labels * sizeof(struct nvdimm_label) >=
-		    nv->label_area_size)
-			break;
-	}
-	num_labels = (nv->label_area_size - index_size) /
-	    sizeof(struct nvdimm_label);
-	bitfield_size = roundup2(num_labels, 8) / 8;
-	indices = malloc(2 * index_size, M_NVDIMM, M_WAITOK);
-	error = read_label_area(nv, (void *)indices, 0, 2 * index_size);
-	if (error != 0) {
-		free(indices, M_NVDIMM);
-		return (error);
-	}
-	index_0_valid = label_index_is_valid(indices, num_labels, index_size,
-	    0);
-	index_1_valid = label_index_is_valid(indices, num_labels, index_size,
-	    1);
-	if (!index_0_valid && !index_1_valid) {
-		free(indices, M_NVDIMM);
-		return (ENXIO);
-	}
-	if (index_0_valid && index_1_valid &&
-	    (indices[1].seq > indices[0].seq ||
-	    (indices[1].seq == 1 && indices[0].seq == 3)))
-		index_0_valid = false;
-	nv->label_index = malloc(index_size, M_NVDIMM, M_WAITOK);
-	bcopy(indices + (index_0_valid ? 0 : 1), nv->label_index, index_size);
-	free(indices, M_NVDIMM);
-	for (bit_ffc_at((bitstr_t *)nv->label_index->free, 0, num_labels, &n);
-	     n >= 0;
-	     bit_ffc_at((bitstr_t *)nv->label_index->free, n + 1, num_labels,
-	     &n)) {
-		read_label(nv, n);
-	}
-	return (0);
-}
-
-struct nvdimm_dev *
-nvdimm_find_by_handle(nfit_handle_t nv_handle)
-{
-	struct nvdimm_dev *res;
-	device_t *dimms;
-	int i, error, num_dimms;
-
-	res = NULL;
-	error = devclass_get_devices(nvdimm_devclass, &dimms, &num_dimms);
-	if (error != 0)
-		return (NULL);
-	for (i = 0; i < num_dimms; i++) {
-		if (nvdimm_root_get_device_handle(dimms[i]) == nv_handle) {
-			res = device_get_softc(dimms[i]);
-			break;
-		}
-	}
-	free(dimms, M_TEMP);
-	return (res);
-}
-
-static int
-nvdimm_probe(device_t dev)
-{
-
-	return (BUS_PROBE_NOWILDCARD);
-}
-
-static int
-nvdimm_attach(device_t dev)
-{
-	struct nvdimm_dev *nv;
-	ACPI_TABLE_NFIT *nfitbl;
-	ACPI_HANDLE handle;
-	ACPI_STATUS status;
-	int error;
-
-	nv = device_get_softc(dev);
-	handle = nvdimm_root_get_acpi_handle(dev);
-	if (handle == NULL)
-		return (EINVAL);
-	nv->nv_dev = dev;
-	nv->nv_handle = nvdimm_root_get_device_handle(dev);
-
-	status = AcpiGetTable(ACPI_SIG_NFIT, 1, (ACPI_TABLE_HEADER **)&nfitbl);
-	if (ACPI_FAILURE(status)) {
-		if (bootverbose)
-			device_printf(dev, "cannot get NFIT\n");
-		return (ENXIO);
-	}
-	acpi_nfit_get_flush_addrs(nfitbl, nv->nv_handle, &nv->nv_flush_addr,
-	    &nv->nv_flush_addr_cnt);
-	AcpiPutTable(&nfitbl->Header);
-	error = read_label_area_size(nv);
-	if (error == 0) {
-		/*
-		 * Ignoring errors reading labels. Not all NVDIMMs
-		 * support labels and namespaces.
-		 */
-		read_labels(nv);
-	}
-	return (0);
-}
-
-static int
-nvdimm_detach(device_t dev)
-{
-	struct nvdimm_dev *nv;
-	struct nvdimm_label_entry *label, *next;
-
-	nv = device_get_softc(dev);
-	free(nv->nv_flush_addr, M_NVDIMM);
-	free(nv->label_index, M_NVDIMM);
-	SLIST_FOREACH_SAFE(label, &nv->labels, link, next) {
-		SLIST_REMOVE_HEAD(&nv->labels, link);
-		free(label, M_NVDIMM);
-	}
-	return (0);
-}
-
-static int
-nvdimm_suspend(device_t dev)
-{
-
-	return (0);
-}
-
-static int
-nvdimm_resume(device_t dev)
-{
-
-	return (0);
-}
-
 static ACPI_STATUS
 find_dimm(ACPI_HANDLE handle, UINT32 nesting_level, void *context,
     void **return_value)
@@ -424,18 +103,21 @@ nvdimm_root_create_devs(device_t dev, ACPI_TABLE_NFIT 
 	acpi_nfit_get_dimm_ids(nfitbl, &dimm_ids, &num_dimm_ids);
 	for (dimm = dimm_ids; dimm < dimm_ids + num_dimm_ids; dimm++) {
 		dimm_handle = get_dimm_acpi_handle(root_handle, *dimm);
+		if (dimm_handle == NULL)
+			continue;
+
 		child = BUS_ADD_CHILD(dev, 100, "nvdimm", -1);
 		if (child == NULL) {
 			device_printf(dev, "failed to create nvdimm\n");
 			return (ENXIO);
 		}
 		ivars = mallocarray(NVDIMM_ROOT_IVAR_MAX, sizeof(uintptr_t),
-		    M_NVDIMM, M_ZERO | M_WAITOK);
+		    M_NVDIMM_ACPI, M_ZERO | M_WAITOK);
 		device_set_ivars(child, ivars);
 		nvdimm_root_set_acpi_handle(child, dimm_handle);
 		nvdimm_root_set_device_handle(child, *dimm);
 	}
-	free(dimm_ids, M_NVDIMM);
+	free(dimm_ids, M_NVDIMM_ACPI);
 	return (0);
 }
 
@@ -454,18 +136,18 @@ nvdimm_root_create_spas(struct nvdimm_root_dev *dev, A
 			(struct uuid *)(*spa)->RangeGuid);
 		if (spa_type == SPA_TYPE_UNKNOWN)
 			continue;
-		spa_mapping = malloc(sizeof(struct SPA_mapping), M_NVDIMM,
+		spa_mapping = malloc(sizeof(struct SPA_mapping), M_NVDIMM_ACPI,
 		    M_WAITOK | M_ZERO);
 		error = nvdimm_spa_init(spa_mapping, *spa, spa_type);
 		if (error != 0) {
 			nvdimm_spa_fini(spa_mapping);
-			free(spa, M_NVDIMM);
+			free(spa, M_NVDIMM_ACPI);
 			break;
 		}
 		nvdimm_create_namespaces(spa_mapping, nfitbl);
 		SLIST_INSERT_HEAD(&dev->spas, spa_mapping, link);
 	}
-	free(spas, M_NVDIMM);
+	free(spas, M_NVDIMM_ACPI);
 	return (error);
 }
 
@@ -523,7 +205,7 @@ nvdimm_root_detach(device_t dev)
 		nvdimm_destroy_namespaces(spa);
 		nvdimm_spa_fini(spa);
 		SLIST_REMOVE_HEAD(&root->spas, link);
-		free(spa, M_NVDIMM);
+		free(spa, M_NVDIMM_ACPI);
 	}
 	error = bus_generic_detach(dev);
 	if (error != 0)
@@ -532,7 +214,7 @@ nvdimm_root_detach(device_t dev)
 	if (error != 0)
 		return (error);
 	for (i = 0; i < num_children; i++)
-		free(device_get_ivars(children[i]), M_NVDIMM);
+		free(device_get_ivars(children[i]), M_NVDIMM_ACPI);
 	free(children, M_TEMP);
 	error = device_delete_children(dev);
 	return (error);
@@ -578,22 +260,7 @@ nvdimm_root_child_location_str(device_t dev, device_t 
 	return (0);
 }
 
-static device_method_t nvdimm_methods[] = {
-	DEVMETHOD(device_probe, nvdimm_probe),
-	DEVMETHOD(device_attach, nvdimm_attach),
-	DEVMETHOD(device_detach, nvdimm_detach),
-	DEVMETHOD(device_suspend, nvdimm_suspend),
-	DEVMETHOD(device_resume, nvdimm_resume),
-	DEVMETHOD_END
-};
-
-static driver_t	nvdimm_driver = {
-	"nvdimm",
-	nvdimm_methods,
-	sizeof(struct nvdimm_dev),
-};
-
-static device_method_t nvdimm_root_methods[] = {
+static device_method_t nvdimm_acpi_methods[] = {
 	DEVMETHOD(device_probe, nvdimm_root_probe),
 	DEVMETHOD(device_attach, nvdimm_root_attach),
 	DEVMETHOD(device_detach, nvdimm_root_detach),
@@ -604,13 +271,13 @@ static device_method_t nvdimm_root_methods[] = {
 	DEVMETHOD_END
 };
 
-static driver_t	nvdimm_root_driver = {
-	"nvdimm_root",
-	nvdimm_root_methods,
+static driver_t	nvdimm_acpi_driver = {
+	"nvdimm_acpi_root",
+	nvdimm_acpi_methods,
 	sizeof(struct nvdimm_root_dev),
 };
 
-DRIVER_MODULE(nvdimm_root, acpi, nvdimm_root_driver, nvdimm_root_devclass, NULL,
-    NULL);
-DRIVER_MODULE(nvdimm, nvdimm_root, nvdimm_driver, nvdimm_devclass, NULL, NULL);
-MODULE_DEPEND(nvdimm, acpi, 1, 1, 1);
+static devclass_t nvdimm_acpi_root_devclass;
+DRIVER_MODULE(nvdimm_acpi_root, acpi, nvdimm_acpi_driver,
+    nvdimm_acpi_root_devclass, NULL, NULL);
+MODULE_DEPEND(nvdimm_acpi_root, acpi, 1, 1, 1);

Modified: head/sys/dev/nvdimm/nvdimm_var.h
==============================================================================
--- head/sys/dev/nvdimm/nvdimm_var.h	Fri Sep 27 16:27:52 2019	(r352797)
+++ head/sys/dev/nvdimm/nvdimm_var.h	Fri Sep 27 16:32:44 2019	(r352798)
@@ -80,7 +80,7 @@ _Static_assert(sizeof(struct nvdimm_label) == 256, "In
 
 typedef uint32_t nfit_handle_t;
 
-enum nvdimm_root_ivar {
+enum nvdimm_acpi_ivar {
 	NVDIMM_ROOT_IVAR_ACPI_HANDLE,
 	NVDIMM_ROOT_IVAR_DEVICE_HANDLE,
 	NVDIMM_ROOT_IVAR_MAX,
@@ -88,10 +88,6 @@ enum nvdimm_root_ivar {
 __BUS_ACCESSOR(nvdimm_root, acpi_handle, NVDIMM_ROOT, ACPI_HANDLE, ACPI_HANDLE)
 __BUS_ACCESSOR(nvdimm_root, device_handle, NVDIMM_ROOT, DEVICE_HANDLE,
     nfit_handle_t)
-
-struct nvdimm_root_dev {
-	SLIST_HEAD(, SPA_mapping) spas;
-};
 
 struct nvdimm_dev {
 	device_t	nv_dev;

Modified: head/sys/modules/nvdimm/Makefile
==============================================================================
--- head/sys/modules/nvdimm/Makefile	Fri Sep 27 16:27:52 2019	(r352797)
+++ head/sys/modules/nvdimm/Makefile	Fri Sep 27 16:32:44 2019	(r352798)
@@ -4,6 +4,7 @@
 
 KMOD=	nvdimm
 SRCS=	nvdimm.c \
+	nvdimm_acpi.c \
 	nvdimm_nfit.c \
 	nvdimm_ns.c \
 	nvdimm_spa.c


More information about the svn-src-head mailing list