Commit 73b3108d authored by Steve Wahl's avatar Steve Wahl Committed by Dave Hansen
Browse files

x86/platform/uv: Update UV[23] platform code for SNC



Previous Sub-NUMA Clustering changes need not just a count of blades
present, but a count that includes any missing ids for blades not
present; in other words, the range from lowest to highest blade id.

Signed-off-by: default avatarSteve Wahl <steve.wahl@hpe.com>
Signed-off-by: default avatarDave Hansen <dave.hansen@linux.intel.com>
Link: https://lore.kernel.org/all/20230519190752.3297140-9-steve.wahl%40hpe.com
parent 89827568
Loading
Loading
Loading
Loading
+38 −4
Original line number Diff line number Diff line
@@ -1462,11 +1462,37 @@ static int __init decode_uv_systab(void)
	return 0;
}

/*
 * Given a bitmask 'bits' representing presnt blades, numbered
 * starting at 'base', masking off unused high bits of blade number
 * with 'mask', update the minimum and maximum blade numbers that we
 * have found.  (Masking with 'mask' necessary because of BIOS
 * treatment of system partitioning when creating this table we are
 * interpreting.)
 */
static inline void blade_update_min_max(unsigned long bits, int base, int mask, int *min, int *max)
{
	int first, last;

	if (!bits)
		return;
	first = (base + __ffs(bits)) & mask;
	last =  (base + __fls(bits)) & mask;

	if (*min > first)
		*min = first;
	if (*max < last)
		*max = last;
}

/* Set up physical blade translations from UVH_NODE_PRESENT_TABLE */
static __init void boot_init_possible_blades(struct uv_hub_info_s *hub_info)
{
	unsigned long np;
	int i, uv_pb = 0;
	int sock_min = INT_MAX, sock_max = -1, s_mask;

	s_mask = (1 << uv_cpuid.n_skt) - 1;

	if (UVH_NODE_PRESENT_TABLE) {
		pr_info("UV: NODE_PRESENT_DEPTH = %d\n",
@@ -1474,23 +1500,31 @@ static __init void boot_init_possible_blades(struct uv_hub_info_s *hub_info)
		for (i = 0; i < UVH_NODE_PRESENT_TABLE_DEPTH; i++) {
			np = uv_read_local_mmr(UVH_NODE_PRESENT_TABLE + i * 8);
			pr_info("UV: NODE_PRESENT(%d) = 0x%016lx\n", i, np);
			uv_pb += hweight64(np);
			blade_update_min_max(np, i * 64, s_mask, &sock_min, &sock_max);
		}
	}
	if (UVH_NODE_PRESENT_0) {
		np = uv_read_local_mmr(UVH_NODE_PRESENT_0);
		pr_info("UV: NODE_PRESENT_0 = 0x%016lx\n", np);
		uv_pb += hweight64(np);
		blade_update_min_max(np, 0, s_mask, &sock_min, &sock_max);
	}
	if (UVH_NODE_PRESENT_1) {
		np = uv_read_local_mmr(UVH_NODE_PRESENT_1);
		pr_info("UV: NODE_PRESENT_1 = 0x%016lx\n", np);
		uv_pb += hweight64(np);
		blade_update_min_max(np, 64, s_mask, &sock_min, &sock_max);
	}

	/* Only update if we actually found some bits indicating blades present */
	if (sock_max >= sock_min) {
		_min_socket = sock_min;
		_max_socket = sock_max;
		uv_pb = sock_max - sock_min + 1;
	}
	if (uv_possible_blades != uv_pb)
		uv_possible_blades = uv_pb;

	pr_info("UV: number nodes/possible blades %d\n", uv_pb);
	pr_info("UV: number nodes/possible blades %d (%d - %d)\n",
		uv_pb, sock_min, sock_max);
}

static int __init alloc_conv_table(int num_elem, unsigned short **table)