Orange Pi5 kernel

Deprecated Linux kernel 5.10.110 for OrangePi 5/5B/5+ boards

3 Commits   0 Branches   0 Tags
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   1) // SPDX-License-Identifier: GPL-2.0-or-later
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   2) /* -*- mode: c; c-basic-offset: 8; -*-
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   3)  * vim: noexpandtab sw=8 ts=8 sts=0:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   4)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   5)  * Copyright (C) 2004, 2005 Oracle.  All rights reserved.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   6)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   7) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   8) #include <linux/slab.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   9) #include <linux/kernel.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  10) #include <linux/module.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  11) #include <linux/configfs.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  12) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  13) #include "tcp.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  14) #include "nodemanager.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  15) #include "heartbeat.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  16) #include "masklog.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  17) #include "sys.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  18) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  19) /* for now we operate under the assertion that there can be only one
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  20)  * cluster active at a time.  Changing this will require trickling
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  21)  * cluster references throughout where nodes are looked up */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  22) struct o2nm_cluster *o2nm_single_cluster = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  23) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  24) static const char *o2nm_fence_method_desc[O2NM_FENCE_METHODS] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  25) 	"reset",	/* O2NM_FENCE_RESET */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  26) 	"panic",	/* O2NM_FENCE_PANIC */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  27) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  28) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  29) static inline void o2nm_lock_subsystem(void);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  30) static inline void o2nm_unlock_subsystem(void);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  31) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  32) struct o2nm_node *o2nm_get_node_by_num(u8 node_num)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  33) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  34) 	struct o2nm_node *node = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  35) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  36) 	if (node_num >= O2NM_MAX_NODES || o2nm_single_cluster == NULL)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  37) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  38) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  39) 	read_lock(&o2nm_single_cluster->cl_nodes_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  40) 	node = o2nm_single_cluster->cl_nodes[node_num];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  41) 	if (node)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  42) 		config_item_get(&node->nd_item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  43) 	read_unlock(&o2nm_single_cluster->cl_nodes_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  44) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  45) 	return node;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  46) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  47) EXPORT_SYMBOL_GPL(o2nm_get_node_by_num);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  48) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  49) int o2nm_configured_node_map(unsigned long *map, unsigned bytes)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  50) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  51) 	struct o2nm_cluster *cluster = o2nm_single_cluster;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  52) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  53) 	BUG_ON(bytes < (sizeof(cluster->cl_nodes_bitmap)));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  54) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  55) 	if (cluster == NULL)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  56) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  57) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  58) 	read_lock(&cluster->cl_nodes_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  59) 	memcpy(map, cluster->cl_nodes_bitmap, sizeof(cluster->cl_nodes_bitmap));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  60) 	read_unlock(&cluster->cl_nodes_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  61) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  62) 	return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  63) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  64) EXPORT_SYMBOL_GPL(o2nm_configured_node_map);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  65) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  66) static struct o2nm_node *o2nm_node_ip_tree_lookup(struct o2nm_cluster *cluster,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  67) 						  __be32 ip_needle,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  68) 						  struct rb_node ***ret_p,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  69) 						  struct rb_node **ret_parent)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  70) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  71) 	struct rb_node **p = &cluster->cl_node_ip_tree.rb_node;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  72) 	struct rb_node *parent = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  73) 	struct o2nm_node *node, *ret = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  74) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  75) 	while (*p) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  76) 		int cmp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  77) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  78) 		parent = *p;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  79) 		node = rb_entry(parent, struct o2nm_node, nd_ip_node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  80) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  81) 		cmp = memcmp(&ip_needle, &node->nd_ipv4_address,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  82) 				sizeof(ip_needle));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  83) 		if (cmp < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  84) 			p = &(*p)->rb_left;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  85) 		else if (cmp > 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  86) 			p = &(*p)->rb_right;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  87) 		else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  88) 			ret = node;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  89) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  90) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  91) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  92) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  93) 	if (ret_p != NULL)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  94) 		*ret_p = p;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  95) 	if (ret_parent != NULL)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  96) 		*ret_parent = parent;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  97) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  98) 	return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  99) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) struct o2nm_node *o2nm_get_node_by_ip(__be32 addr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) 	struct o2nm_node *node = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) 	struct o2nm_cluster *cluster = o2nm_single_cluster;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) 	if (cluster == NULL)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) 	read_lock(&cluster->cl_nodes_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) 	node = o2nm_node_ip_tree_lookup(cluster, addr, NULL, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) 	if (node)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) 		config_item_get(&node->nd_item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) 	read_unlock(&cluster->cl_nodes_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) 	return node;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) EXPORT_SYMBOL_GPL(o2nm_get_node_by_ip);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) void o2nm_node_put(struct o2nm_node *node)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) 	config_item_put(&node->nd_item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) EXPORT_SYMBOL_GPL(o2nm_node_put);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) void o2nm_node_get(struct o2nm_node *node)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) 	config_item_get(&node->nd_item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) EXPORT_SYMBOL_GPL(o2nm_node_get);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) u8 o2nm_this_node(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) 	u8 node_num = O2NM_MAX_NODES;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) 	if (o2nm_single_cluster && o2nm_single_cluster->cl_has_local)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) 		node_num = o2nm_single_cluster->cl_local_node;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) 	return node_num;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) EXPORT_SYMBOL_GPL(o2nm_this_node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) /* node configfs bits */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) static struct o2nm_cluster *to_o2nm_cluster(struct config_item *item)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) 	return item ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) 		container_of(to_config_group(item), struct o2nm_cluster,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) 			     cl_group)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) 		: NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) static struct o2nm_node *to_o2nm_node(struct config_item *item)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) 	return item ? container_of(item, struct o2nm_node, nd_item) : NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) static void o2nm_node_release(struct config_item *item)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) 	struct o2nm_node *node = to_o2nm_node(item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) 	kfree(node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) static ssize_t o2nm_node_num_show(struct config_item *item, char *page)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) 	return sprintf(page, "%d\n", to_o2nm_node(item)->nd_num);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) static struct o2nm_cluster *to_o2nm_cluster_from_node(struct o2nm_node *node)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) 	/* through the first node_set .parent
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) 	 * mycluster/nodes/mynode == o2nm_cluster->o2nm_node_group->o2nm_node */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) 	if (node->nd_item.ci_parent)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) 		return to_o2nm_cluster(node->nd_item.ci_parent->ci_parent);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) 	else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) 		return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) enum {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) 	O2NM_NODE_ATTR_NUM = 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) 	O2NM_NODE_ATTR_PORT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) 	O2NM_NODE_ATTR_ADDRESS,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) static ssize_t o2nm_node_num_store(struct config_item *item, const char *page,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) 				   size_t count)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) 	struct o2nm_node *node = to_o2nm_node(item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) 	struct o2nm_cluster *cluster;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) 	unsigned long tmp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) 	char *p = (char *)page;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) 	int ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) 	tmp = simple_strtoul(p, &p, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) 	if (!p || (*p && (*p != '\n')))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) 	if (tmp >= O2NM_MAX_NODES)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) 		return -ERANGE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) 	/* once we're in the cl_nodes tree networking can look us up by
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) 	 * node number and try to use our address and port attributes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) 	 * to connect to this node.. make sure that they've been set
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) 	 * before writing the node attribute? */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) 	if (!test_bit(O2NM_NODE_ATTR_ADDRESS, &node->nd_set_attributes) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) 	    !test_bit(O2NM_NODE_ATTR_PORT, &node->nd_set_attributes))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) 		return -EINVAL; /* XXX */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) 	o2nm_lock_subsystem();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) 	cluster = to_o2nm_cluster_from_node(node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) 	if (!cluster) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) 		o2nm_unlock_subsystem();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) 	write_lock(&cluster->cl_nodes_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) 	if (cluster->cl_nodes[tmp])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) 		ret = -EEXIST;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) 	else if (test_and_set_bit(O2NM_NODE_ATTR_NUM,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) 			&node->nd_set_attributes))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) 		ret = -EBUSY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) 	else  {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) 		cluster->cl_nodes[tmp] = node;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) 		node->nd_num = tmp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) 		set_bit(tmp, cluster->cl_nodes_bitmap);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) 	write_unlock(&cluster->cl_nodes_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) 	o2nm_unlock_subsystem();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) 	if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) 		return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) 	return count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) static ssize_t o2nm_node_ipv4_port_show(struct config_item *item, char *page)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) 	return sprintf(page, "%u\n", ntohs(to_o2nm_node(item)->nd_ipv4_port));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) static ssize_t o2nm_node_ipv4_port_store(struct config_item *item,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) 					 const char *page, size_t count)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) 	struct o2nm_node *node = to_o2nm_node(item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) 	unsigned long tmp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) 	char *p = (char *)page;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) 	tmp = simple_strtoul(p, &p, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) 	if (!p || (*p && (*p != '\n')))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) 	if (tmp == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) 	if (tmp >= (u16)-1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) 		return -ERANGE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) 	if (test_and_set_bit(O2NM_NODE_ATTR_PORT, &node->nd_set_attributes))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) 		return -EBUSY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) 	node->nd_ipv4_port = htons(tmp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) 	return count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) static ssize_t o2nm_node_ipv4_address_show(struct config_item *item, char *page)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) 	return sprintf(page, "%pI4\n", &to_o2nm_node(item)->nd_ipv4_address);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) static ssize_t o2nm_node_ipv4_address_store(struct config_item *item,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) 					    const char *page,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) 					    size_t count)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) 	struct o2nm_node *node = to_o2nm_node(item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) 	struct o2nm_cluster *cluster;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) 	int ret, i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) 	struct rb_node **p, *parent;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) 	unsigned int octets[4];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) 	__be32 ipv4_addr = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) 	ret = sscanf(page, "%3u.%3u.%3u.%3u", &octets[3], &octets[2],
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) 		     &octets[1], &octets[0]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) 	if (ret != 4)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) 	for (i = 0; i < ARRAY_SIZE(octets); i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) 		if (octets[i] > 255)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) 			return -ERANGE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) 		be32_add_cpu(&ipv4_addr, octets[i] << (i * 8));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) 	o2nm_lock_subsystem();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) 	cluster = to_o2nm_cluster_from_node(node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) 	if (!cluster) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) 		o2nm_unlock_subsystem();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) 	ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) 	write_lock(&cluster->cl_nodes_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) 	if (o2nm_node_ip_tree_lookup(cluster, ipv4_addr, &p, &parent))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) 		ret = -EEXIST;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) 	else if (test_and_set_bit(O2NM_NODE_ATTR_ADDRESS,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) 			&node->nd_set_attributes))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) 		ret = -EBUSY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) 	else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) 		rb_link_node(&node->nd_ip_node, parent, p);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) 		rb_insert_color(&node->nd_ip_node, &cluster->cl_node_ip_tree);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) 	write_unlock(&cluster->cl_nodes_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) 	o2nm_unlock_subsystem();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) 	if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) 		return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) 	memcpy(&node->nd_ipv4_address, &ipv4_addr, sizeof(ipv4_addr));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) 	return count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) static ssize_t o2nm_node_local_show(struct config_item *item, char *page)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) 	return sprintf(page, "%d\n", to_o2nm_node(item)->nd_local);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) static ssize_t o2nm_node_local_store(struct config_item *item, const char *page,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) 				     size_t count)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) 	struct o2nm_node *node = to_o2nm_node(item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) 	struct o2nm_cluster *cluster;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) 	unsigned long tmp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) 	char *p = (char *)page;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) 	ssize_t ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) 	tmp = simple_strtoul(p, &p, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) 	if (!p || (*p && (*p != '\n')))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) 	tmp = !!tmp; /* boolean of whether this node wants to be local */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) 	/* setting local turns on networking rx for now so we require having
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) 	 * set everything else first */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) 	if (!test_bit(O2NM_NODE_ATTR_ADDRESS, &node->nd_set_attributes) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) 	    !test_bit(O2NM_NODE_ATTR_NUM, &node->nd_set_attributes) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) 	    !test_bit(O2NM_NODE_ATTR_PORT, &node->nd_set_attributes))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) 		return -EINVAL; /* XXX */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) 	o2nm_lock_subsystem();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) 	cluster = to_o2nm_cluster_from_node(node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) 	if (!cluster) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) 		ret = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) 	/* the only failure case is trying to set a new local node
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) 	 * when a different one is already set */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) 	if (tmp && tmp == cluster->cl_has_local &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) 	    cluster->cl_local_node != node->nd_num) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) 		ret = -EBUSY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) 	/* bring up the rx thread if we're setting the new local node. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) 	if (tmp && !cluster->cl_has_local) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) 		ret = o2net_start_listening(node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) 		if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) 			goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) 	if (!tmp && cluster->cl_has_local &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) 	    cluster->cl_local_node == node->nd_num) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) 		o2net_stop_listening(node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) 		cluster->cl_local_node = O2NM_INVALID_NODE_NUM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) 	node->nd_local = tmp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) 	if (node->nd_local) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) 		cluster->cl_has_local = tmp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) 		cluster->cl_local_node = node->nd_num;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) 	ret = count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) 	o2nm_unlock_subsystem();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) 	return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) CONFIGFS_ATTR(o2nm_node_, num);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) CONFIGFS_ATTR(o2nm_node_, ipv4_port);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) CONFIGFS_ATTR(o2nm_node_, ipv4_address);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390) CONFIGFS_ATTR(o2nm_node_, local);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) static struct configfs_attribute *o2nm_node_attrs[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393) 	&o2nm_node_attr_num,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) 	&o2nm_node_attr_ipv4_port,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) 	&o2nm_node_attr_ipv4_address,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) 	&o2nm_node_attr_local,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) 	NULL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) static struct configfs_item_operations o2nm_node_item_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) 	.release		= o2nm_node_release,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) static const struct config_item_type o2nm_node_type = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405) 	.ct_item_ops	= &o2nm_node_item_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) 	.ct_attrs	= o2nm_node_attrs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) 	.ct_owner	= THIS_MODULE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) /* node set */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) struct o2nm_node_group {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413) 	struct config_group ns_group;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) 	/* some stuff? */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417) #if 0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) static struct o2nm_node_group *to_o2nm_node_group(struct config_group *group)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) 	return group ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421) 		container_of(group, struct o2nm_node_group, ns_group)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) 		: NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) static ssize_t o2nm_cluster_attr_write(const char *page, ssize_t count,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427)                                        unsigned int *val)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) 	unsigned long tmp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) 	char *p = (char *)page;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) 	tmp = simple_strtoul(p, &p, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) 	if (!p || (*p && (*p != '\n')))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) 	if (tmp == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) 		return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) 	if (tmp >= (u32)-1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) 		return -ERANGE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) 	*val = tmp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443) 	return count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446) static ssize_t o2nm_cluster_idle_timeout_ms_show(struct config_item *item,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447) 	char *page)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449) 	return sprintf(page, "%u\n", to_o2nm_cluster(item)->cl_idle_timeout_ms);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452) static ssize_t o2nm_cluster_idle_timeout_ms_store(struct config_item *item,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) 	const char *page, size_t count)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455) 	struct o2nm_cluster *cluster = to_o2nm_cluster(item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) 	ssize_t ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457) 	unsigned int val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) 	ret =  o2nm_cluster_attr_write(page, count, &val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461) 	if (ret > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462) 		if (cluster->cl_idle_timeout_ms != val
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463) 			&& o2net_num_connected_peers()) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464) 			mlog(ML_NOTICE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465) 			     "o2net: cannot change idle timeout after "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466) 			     "the first peer has agreed to it."
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467) 			     "  %d connected peers\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468) 			     o2net_num_connected_peers());
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469) 			ret = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470) 		} else if (val <= cluster->cl_keepalive_delay_ms) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471) 			mlog(ML_NOTICE, "o2net: idle timeout must be larger "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472) 			     "than keepalive delay\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473) 			ret = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475) 			cluster->cl_idle_timeout_ms = val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479) 	return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 480) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 481) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 482) static ssize_t o2nm_cluster_keepalive_delay_ms_show(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 483) 	struct config_item *item, char *page)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 484) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 485) 	return sprintf(page, "%u\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 486) 			to_o2nm_cluster(item)->cl_keepalive_delay_ms);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 487) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 488) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 489) static ssize_t o2nm_cluster_keepalive_delay_ms_store(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 490) 	struct config_item *item, const char *page, size_t count)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 491) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 492) 	struct o2nm_cluster *cluster = to_o2nm_cluster(item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 493) 	ssize_t ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 494) 	unsigned int val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 495) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 496) 	ret =  o2nm_cluster_attr_write(page, count, &val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 497) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 498) 	if (ret > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 499) 		if (cluster->cl_keepalive_delay_ms != val
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 500) 		    && o2net_num_connected_peers()) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 501) 			mlog(ML_NOTICE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 502) 			     "o2net: cannot change keepalive delay after"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 503) 			     " the first peer has agreed to it."
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 504) 			     "  %d connected peers\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 505) 			     o2net_num_connected_peers());
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 506) 			ret = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 507) 		} else if (val >= cluster->cl_idle_timeout_ms) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 508) 			mlog(ML_NOTICE, "o2net: keepalive delay must be "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 509) 			     "smaller than idle timeout\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 510) 			ret = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 511) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 512) 			cluster->cl_keepalive_delay_ms = val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 513) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 514) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 515) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 516) 	return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 517) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 518) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 519) static ssize_t o2nm_cluster_reconnect_delay_ms_show(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 520) 	struct config_item *item, char *page)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 521) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 522) 	return sprintf(page, "%u\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 523) 			to_o2nm_cluster(item)->cl_reconnect_delay_ms);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 524) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 525) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 526) static ssize_t o2nm_cluster_reconnect_delay_ms_store(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 527) 	struct config_item *item, const char *page, size_t count)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 528) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 529) 	return o2nm_cluster_attr_write(page, count,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 530)                                &to_o2nm_cluster(item)->cl_reconnect_delay_ms);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 531) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 532) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 533) static ssize_t o2nm_cluster_fence_method_show(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 534) 	struct config_item *item, char *page)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 535) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 536) 	struct o2nm_cluster *cluster = to_o2nm_cluster(item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 537) 	ssize_t ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 538) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 539) 	if (cluster)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 540) 		ret = sprintf(page, "%s\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 541) 			      o2nm_fence_method_desc[cluster->cl_fence_method]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 542) 	return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 543) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 544) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 545) static ssize_t o2nm_cluster_fence_method_store(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 546) 	struct config_item *item, const char *page, size_t count)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 547) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 548) 	unsigned int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 549) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 550) 	if (page[count - 1] != '\n')
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 551) 		goto bail;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 552) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 553) 	for (i = 0; i < O2NM_FENCE_METHODS; ++i) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 554) 		if (count != strlen(o2nm_fence_method_desc[i]) + 1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 555) 			continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 556) 		if (strncasecmp(page, o2nm_fence_method_desc[i], count - 1))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 557) 			continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 558) 		if (to_o2nm_cluster(item)->cl_fence_method != i) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 559) 			printk(KERN_INFO "ocfs2: Changing fence method to %s\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 560) 			       o2nm_fence_method_desc[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 561) 			to_o2nm_cluster(item)->cl_fence_method = i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 562) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 563) 		return count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 564) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 565) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 566) bail:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 567) 	return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 568) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 569) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 570) CONFIGFS_ATTR(o2nm_cluster_, idle_timeout_ms);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 571) CONFIGFS_ATTR(o2nm_cluster_, keepalive_delay_ms);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 572) CONFIGFS_ATTR(o2nm_cluster_, reconnect_delay_ms);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 573) CONFIGFS_ATTR(o2nm_cluster_, fence_method);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 574) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 575) static struct configfs_attribute *o2nm_cluster_attrs[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 576) 	&o2nm_cluster_attr_idle_timeout_ms,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 577) 	&o2nm_cluster_attr_keepalive_delay_ms,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 578) 	&o2nm_cluster_attr_reconnect_delay_ms,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 579) 	&o2nm_cluster_attr_fence_method,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 580) 	NULL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 581) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 582) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 583) static struct config_item *o2nm_node_group_make_item(struct config_group *group,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 584) 						     const char *name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 585) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 586) 	struct o2nm_node *node = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 587) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 588) 	if (strlen(name) > O2NM_MAX_NAME_LEN)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 589) 		return ERR_PTR(-ENAMETOOLONG);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 590) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 591) 	node = kzalloc(sizeof(struct o2nm_node), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 592) 	if (node == NULL)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 593) 		return ERR_PTR(-ENOMEM);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 594) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 595) 	strcpy(node->nd_name, name); /* use item.ci_namebuf instead? */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 596) 	config_item_init_type_name(&node->nd_item, name, &o2nm_node_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 597) 	spin_lock_init(&node->nd_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 598) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 599) 	mlog(ML_CLUSTER, "o2nm: Registering node %s\n", name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 600) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 601) 	return &node->nd_item;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 602) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 603) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 604) static void o2nm_node_group_drop_item(struct config_group *group,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 605) 				      struct config_item *item)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 606) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 607) 	struct o2nm_node *node = to_o2nm_node(item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 608) 	struct o2nm_cluster *cluster = to_o2nm_cluster(group->cg_item.ci_parent);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 609) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 610) 	if (cluster->cl_nodes[node->nd_num] == node) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 611) 		o2net_disconnect_node(node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 612) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 613) 		if (cluster->cl_has_local &&
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 614) 		    (cluster->cl_local_node == node->nd_num)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 615) 			cluster->cl_has_local = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 616) 			cluster->cl_local_node = O2NM_INVALID_NODE_NUM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 617) 			o2net_stop_listening(node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 618) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 619) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 620) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 621) 	/* XXX call into net to stop this node from trading messages */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 622) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 623) 	write_lock(&cluster->cl_nodes_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 624) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 625) 	/* XXX sloppy */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 626) 	if (node->nd_ipv4_address)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 627) 		rb_erase(&node->nd_ip_node, &cluster->cl_node_ip_tree);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 628) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 629) 	/* nd_num might be 0 if the node number hasn't been set.. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 630) 	if (cluster->cl_nodes[node->nd_num] == node) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 631) 		cluster->cl_nodes[node->nd_num] = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 632) 		clear_bit(node->nd_num, cluster->cl_nodes_bitmap);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 633) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 634) 	write_unlock(&cluster->cl_nodes_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 635) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 636) 	mlog(ML_CLUSTER, "o2nm: Unregistered node %s\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 637) 	     config_item_name(&node->nd_item));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 638) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 639) 	config_item_put(item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 640) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 641) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 642) static struct configfs_group_operations o2nm_node_group_group_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 643) 	.make_item	= o2nm_node_group_make_item,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 644) 	.drop_item	= o2nm_node_group_drop_item,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 645) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 646) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 647) static const struct config_item_type o2nm_node_group_type = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 648) 	.ct_group_ops	= &o2nm_node_group_group_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 649) 	.ct_owner	= THIS_MODULE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 650) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 651) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 652) /* cluster */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 653) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 654) static void o2nm_cluster_release(struct config_item *item)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 655) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 656) 	struct o2nm_cluster *cluster = to_o2nm_cluster(item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 657) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 658) 	kfree(cluster);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 659) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 660) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 661) static struct configfs_item_operations o2nm_cluster_item_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 662) 	.release	= o2nm_cluster_release,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 663) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 664) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 665) static const struct config_item_type o2nm_cluster_type = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 666) 	.ct_item_ops	= &o2nm_cluster_item_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 667) 	.ct_attrs	= o2nm_cluster_attrs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 668) 	.ct_owner	= THIS_MODULE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 669) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 670) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 671) /* cluster set */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 672) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 673) struct o2nm_cluster_group {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 674) 	struct configfs_subsystem cs_subsys;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 675) 	/* some stuff? */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 676) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 677) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 678) #if 0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 679) static struct o2nm_cluster_group *to_o2nm_cluster_group(struct config_group *group)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 680) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 681) 	return group ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 682) 		container_of(to_configfs_subsystem(group), struct o2nm_cluster_group, cs_subsys)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 683) 	       : NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 684) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 685) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 686) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 687) static struct config_group *o2nm_cluster_group_make_group(struct config_group *group,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 688) 							  const char *name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 689) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 690) 	struct o2nm_cluster *cluster = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 691) 	struct o2nm_node_group *ns = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 692) 	struct config_group *o2hb_group = NULL, *ret = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 693) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 694) 	/* this runs under the parent dir's i_mutex; there can be only
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 695) 	 * one caller in here at a time */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 696) 	if (o2nm_single_cluster)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 697) 		return ERR_PTR(-ENOSPC);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 698) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 699) 	cluster = kzalloc(sizeof(struct o2nm_cluster), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 700) 	ns = kzalloc(sizeof(struct o2nm_node_group), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 701) 	o2hb_group = o2hb_alloc_hb_set();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 702) 	if (cluster == NULL || ns == NULL || o2hb_group == NULL)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 703) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 704) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 705) 	config_group_init_type_name(&cluster->cl_group, name,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 706) 				    &o2nm_cluster_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 707) 	configfs_add_default_group(&ns->ns_group, &cluster->cl_group);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 708) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 709) 	config_group_init_type_name(&ns->ns_group, "node",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 710) 				    &o2nm_node_group_type);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 711) 	configfs_add_default_group(o2hb_group, &cluster->cl_group);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 712) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 713) 	rwlock_init(&cluster->cl_nodes_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 714) 	cluster->cl_node_ip_tree = RB_ROOT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 715) 	cluster->cl_reconnect_delay_ms = O2NET_RECONNECT_DELAY_MS_DEFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 716) 	cluster->cl_idle_timeout_ms    = O2NET_IDLE_TIMEOUT_MS_DEFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 717) 	cluster->cl_keepalive_delay_ms = O2NET_KEEPALIVE_DELAY_MS_DEFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 718) 	cluster->cl_fence_method       = O2NM_FENCE_RESET;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 719) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 720) 	ret = &cluster->cl_group;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 721) 	o2nm_single_cluster = cluster;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 722) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 723) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 724) 	if (ret == NULL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 725) 		kfree(cluster);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 726) 		kfree(ns);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 727) 		o2hb_free_hb_set(o2hb_group);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 728) 		ret = ERR_PTR(-ENOMEM);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 729) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 730) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 731) 	return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 732) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 733) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 734) static void o2nm_cluster_group_drop_item(struct config_group *group, struct config_item *item)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 735) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 736) 	struct o2nm_cluster *cluster = to_o2nm_cluster(item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 737) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 738) 	BUG_ON(o2nm_single_cluster != cluster);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 739) 	o2nm_single_cluster = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 740) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 741) 	configfs_remove_default_groups(&cluster->cl_group);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 742) 	config_item_put(item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 743) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 744) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 745) static struct configfs_group_operations o2nm_cluster_group_group_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 746) 	.make_group	= o2nm_cluster_group_make_group,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 747) 	.drop_item	= o2nm_cluster_group_drop_item,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 748) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 749) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 750) static const struct config_item_type o2nm_cluster_group_type = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 751) 	.ct_group_ops	= &o2nm_cluster_group_group_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 752) 	.ct_owner	= THIS_MODULE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 753) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 754) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 755) static struct o2nm_cluster_group o2nm_cluster_group = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 756) 	.cs_subsys = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 757) 		.su_group = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 758) 			.cg_item = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 759) 				.ci_namebuf = "cluster",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 760) 				.ci_type = &o2nm_cluster_group_type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 761) 			},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 762) 		},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 763) 	},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 764) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 765) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 766) static inline void o2nm_lock_subsystem(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 767) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 768) 	mutex_lock(&o2nm_cluster_group.cs_subsys.su_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 769) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 770) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 771) static inline void o2nm_unlock_subsystem(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 772) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 773) 	mutex_unlock(&o2nm_cluster_group.cs_subsys.su_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 774) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 775) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 776) int o2nm_depend_item(struct config_item *item)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 777) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 778) 	return configfs_depend_item(&o2nm_cluster_group.cs_subsys, item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 779) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 780) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 781) void o2nm_undepend_item(struct config_item *item)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 782) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 783) 	configfs_undepend_item(item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 784) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 785) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 786) int o2nm_depend_this_node(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 787) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 788) 	int ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 789) 	struct o2nm_node *local_node;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 790) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 791) 	local_node = o2nm_get_node_by_num(o2nm_this_node());
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 792) 	if (!local_node) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 793) 		ret = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 794) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 795) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 796) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 797) 	ret = o2nm_depend_item(&local_node->nd_item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 798) 	o2nm_node_put(local_node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 799) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 800) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 801) 	return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 802) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 803) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 804) void o2nm_undepend_this_node(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 805) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 806) 	struct o2nm_node *local_node;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 807) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 808) 	local_node = o2nm_get_node_by_num(o2nm_this_node());
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 809) 	BUG_ON(!local_node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 810) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 811) 	o2nm_undepend_item(&local_node->nd_item);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 812) 	o2nm_node_put(local_node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 813) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 814) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 815) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 816) static void __exit exit_o2nm(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 817) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 818) 	/* XXX sync with hb callbacks and shut down hb? */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 819) 	o2net_unregister_hb_callbacks();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 820) 	configfs_unregister_subsystem(&o2nm_cluster_group.cs_subsys);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 821) 	o2cb_sys_shutdown();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 822) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 823) 	o2net_exit();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 824) 	o2hb_exit();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 825) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 826) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 827) static int __init init_o2nm(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 828) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 829) 	int ret = -1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 830) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 831) 	o2hb_init();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 832) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 833) 	ret = o2net_init();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 834) 	if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 835) 		goto out_o2hb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 836) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 837) 	ret = o2net_register_hb_callbacks();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 838) 	if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 839) 		goto out_o2net;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 840) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 841) 	config_group_init(&o2nm_cluster_group.cs_subsys.su_group);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 842) 	mutex_init(&o2nm_cluster_group.cs_subsys.su_mutex);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 843) 	ret = configfs_register_subsystem(&o2nm_cluster_group.cs_subsys);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 844) 	if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 845) 		printk(KERN_ERR "nodemanager: Registration returned %d\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 846) 		goto out_callbacks;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 847) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 848) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 849) 	ret = o2cb_sys_init();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 850) 	if (!ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 851) 		goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 852) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 853) 	configfs_unregister_subsystem(&o2nm_cluster_group.cs_subsys);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 854) out_callbacks:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 855) 	o2net_unregister_hb_callbacks();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 856) out_o2net:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 857) 	o2net_exit();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 858) out_o2hb:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 859) 	o2hb_exit();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 860) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 861) 	return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 862) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 863) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 864) MODULE_AUTHOR("Oracle");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 865) MODULE_LICENSE("GPL");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 866) MODULE_DESCRIPTION("OCFS2 cluster management");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 867) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 868) module_init(init_o2nm)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 869) module_exit(exit_o2nm)