Commit 4dfa6418 authored by Dave Jiang's avatar Dave Jiang
Browse files

Merge branch 'for-6.18/cxl-update-access-coordinates' into cxl-for-next

Update the CXL memory hotplug notifier to update the NUMA node access
coordinates directly rather than go through the HMAT memory hotplug
notifier.
parents a4144081 e99ecbc4
Loading
Loading
Loading
Loading
+0 −34
Original line number Diff line number Diff line
@@ -74,7 +74,6 @@ struct memory_target {
	struct node_cache_attrs cache_attrs;
	u8 gen_port_device_handle[ACPI_SRAT_DEVICE_HANDLE_SIZE];
	bool registered;
	bool ext_updated;	/* externally updated */
};

struct memory_initiator {
@@ -368,35 +367,6 @@ static void hmat_update_target_access(struct memory_target *target,
	}
}

int hmat_update_target_coordinates(int nid, struct access_coordinate *coord,
				   enum access_coordinate_class access)
{
	struct memory_target *target;
	int pxm;

	if (nid == NUMA_NO_NODE)
		return -EINVAL;

	pxm = node_to_pxm(nid);
	guard(mutex)(&target_lock);
	target = find_mem_target(pxm);
	if (!target)
		return -ENODEV;

	hmat_update_target_access(target, ACPI_HMAT_READ_LATENCY,
				  coord->read_latency, access);
	hmat_update_target_access(target, ACPI_HMAT_WRITE_LATENCY,
				  coord->write_latency, access);
	hmat_update_target_access(target, ACPI_HMAT_READ_BANDWIDTH,
				  coord->read_bandwidth, access);
	hmat_update_target_access(target, ACPI_HMAT_WRITE_BANDWIDTH,
				  coord->write_bandwidth, access);
	target->ext_updated = true;

	return 0;
}
EXPORT_SYMBOL_GPL(hmat_update_target_coordinates);

static __init void hmat_add_locality(struct acpi_hmat_locality *hmat_loc)
{
	struct memory_locality *loc;
@@ -773,10 +743,6 @@ static void hmat_update_target_attrs(struct memory_target *target,
	u32 best = 0;
	int i;

	/* Don't update if an external agent has changed the data.  */
	if (target->ext_updated)
		return;

	/* Don't update for generic port if there's no device handle */
	if ((access == NODE_ACCESS_CLASS_GENPORT_SINK_LOCAL ||
	     access == NODE_ACCESS_CLASS_GENPORT_SINK_CPU) &&
+38 −0
Original line number Diff line number Diff line
@@ -248,6 +248,44 @@ void node_set_perf_attrs(unsigned int nid, struct access_coordinate *coord,
}
EXPORT_SYMBOL_GPL(node_set_perf_attrs);

/**
 * node_update_perf_attrs - Update the performance values for given access class
 * @nid: Node identifier to be updated
 * @coord: Heterogeneous memory performance coordinates
 * @access: The access class for the given attributes
 */
void node_update_perf_attrs(unsigned int nid, struct access_coordinate *coord,
			    enum access_coordinate_class access)
{
	struct node_access_nodes *access_node;
	struct node *node;
	int i;

	if (WARN_ON_ONCE(!node_online(nid)))
		return;

	node = node_devices[nid];
	list_for_each_entry(access_node, &node->access_list, list_node) {
		if (access_node->access != access)
			continue;

		access_node->coord = *coord;
		for (i = 0; access_attrs[i]; i++) {
			sysfs_notify(&access_node->dev.kobj,
				     NULL, access_attrs[i]->name);
		}
		break;
	}

	/* When setting CPU access coordinates, update mempolicy */
	if (access != ACCESS_COORDINATE_CPU)
		return;

	if (mempolicy_set_node_perf(nid, coord))
		pr_info("failed to set mempolicy attrs for node %d\n", nid);
}
EXPORT_SYMBOL_GPL(node_update_perf_attrs);

/**
 * struct node_cache_info - Internal tracking for memory node caches
 * @dev:	Device represeting the cache level
+0 −11
Original line number Diff line number Diff line
@@ -1075,14 +1075,3 @@ void cxl_region_perf_data_calculate(struct cxl_region *cxlr,
		cxlr->coord[i].write_bandwidth += perf->coord[i].write_bandwidth;
	}
}

int cxl_update_hmat_access_coordinates(int nid, struct cxl_region *cxlr,
				       enum access_coordinate_class access)
{
	return hmat_update_target_coordinates(nid, &cxlr->coord[access], access);
}

bool cxl_need_node_perf_attrs_update(int nid)
{
	return !acpi_node_backed_by_real_pxm(nid);
}
+0 −3
Original line number Diff line number Diff line
@@ -141,9 +141,6 @@ bool cxl_memdev_has_poison_cmd(struct cxl_memdev *cxlmd,

long cxl_pci_get_latency(struct pci_dev *pdev);
int cxl_pci_get_bandwidth(struct pci_dev *pdev, struct access_coordinate *c);
int cxl_update_hmat_access_coordinates(int nid, struct cxl_region *cxlr,
				       enum access_coordinate_class access);
bool cxl_need_node_perf_attrs_update(int nid);
int cxl_port_get_switch_dport_bandwidth(struct cxl_port *port,
					struct access_coordinate *c);

+12 −8
Original line number Diff line number Diff line
@@ -32,6 +32,12 @@
 * 3. Decoder targets
 */

/*
 * nodemask that sets per node when the access_coordinates for the node has
 * been updated by the CXL memory hotplug notifier.
 */
static nodemask_t nodemask_region_seen = NODE_MASK_NONE;

static struct cxl_region *to_cxl_region(struct device *dev);

#define __ACCESS_ATTR_RO(_level, _name) {				\
@@ -2442,13 +2448,7 @@ static bool cxl_region_update_coordinates(struct cxl_region *cxlr, int nid)

	for (int i = 0; i < ACCESS_COORDINATE_MAX; i++) {
		if (cxlr->coord[i].read_bandwidth) {
			rc = 0;
			if (cxl_need_node_perf_attrs_update(nid))
				node_set_perf_attrs(nid, &cxlr->coord[i], i);
			else
				rc = cxl_update_hmat_access_coordinates(nid, cxlr, i);

			if (rc == 0)
			node_update_perf_attrs(nid, &cxlr->coord[i], i);
			cset++;
		}
	}
@@ -2487,6 +2487,10 @@ static int cxl_region_perf_attrs_callback(struct notifier_block *nb,
	if (nid != region_nid)
		return NOTIFY_DONE;

	/* No action needed if node bit already set */
	if (node_test_and_set(nid, nodemask_region_seen))
		return NOTIFY_DONE;

	if (!cxl_region_update_coordinates(cxlr, nid))
		return NOTIFY_DONE;

Loading