[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]

[Cluster-devel] cluster/rgmanager ChangeLog src/resources/clus ...



CVSROOT:	/cvs/cluster
Module name:	cluster
Changes by:	lhh sourceware org	2007-11-30 20:06:55

Modified files:
	rgmanager      : ChangeLog 
	rgmanager/src/resources: clusterfs.sh fs.sh ocf-shellfuncs 
	                         service.sh vm.sh 
	rgmanager/src/utils: clulog.c clustat.c clusvcadm.c 

Log message:
	Merges from RHEL5 branch - round 1.

Patches:
http://sourceware.org/cgi-bin/cvsweb.cgi/cluster/rgmanager/ChangeLog.diff?cvsroot=cluster&r1=1.59&r2=1.60
http://sourceware.org/cgi-bin/cvsweb.cgi/cluster/rgmanager/src/resources/clusterfs.sh.diff?cvsroot=cluster&r1=1.19&r2=1.20
http://sourceware.org/cgi-bin/cvsweb.cgi/cluster/rgmanager/src/resources/fs.sh.diff?cvsroot=cluster&r1=1.23&r2=1.24
http://sourceware.org/cgi-bin/cvsweb.cgi/cluster/rgmanager/src/resources/ocf-shellfuncs.diff?cvsroot=cluster&r1=1.4&r2=1.5
http://sourceware.org/cgi-bin/cvsweb.cgi/cluster/rgmanager/src/resources/service.sh.diff?cvsroot=cluster&r1=1.11&r2=1.12
http://sourceware.org/cgi-bin/cvsweb.cgi/cluster/rgmanager/src/resources/vm.sh.diff?cvsroot=cluster&r1=1.7&r2=1.8
http://sourceware.org/cgi-bin/cvsweb.cgi/cluster/rgmanager/src/utils/clulog.c.diff?cvsroot=cluster&r1=1.4&r2=1.5
http://sourceware.org/cgi-bin/cvsweb.cgi/cluster/rgmanager/src/utils/clustat.c.diff?cvsroot=cluster&r1=1.35&r2=1.36
http://sourceware.org/cgi-bin/cvsweb.cgi/cluster/rgmanager/src/utils/clusvcadm.c.diff?cvsroot=cluster&r1=1.22&r2=1.23

--- cluster/rgmanager/ChangeLog	2007/08/30 16:09:38	1.59
+++ cluster/rgmanager/ChangeLog	2007/11/30 20:06:55	1.60
@@ -1,3 +1,7 @@
+2007-11-30 Lon Hohberger <lhh at redhat.com>
+	* src/resources/*: Merge from RHEL5 branch.
+	* src/utils/*: Merge from RHEL5 branch.
+
 2007-08-30 Lon Hohberger <lhh at redhat.com>
 	* src/daemons/restree.c, rg_state.c: Fix tree-restart bug
 	This is another part of #229650
--- cluster/rgmanager/src/resources/clusterfs.sh	2007/05/21 15:58:04	1.19
+++ cluster/rgmanager/src/resources/clusterfs.sh	2007/11/30 20:06:55	1.20
@@ -133,6 +133,18 @@
 	    <content type="string"/>
         </parameter>
 
+	<parameter name="self_fence">
+	    <longdesc lang="en">
+	        If set and unmounting the file system fails, the node will
+		immediately reboot.  Generally, this is used in conjunction
+		with force-unmount support, but it is not required.
+	    </longdesc>
+	    <shortdesc lang="en">
+	        Seppuku Unmount
+	    </shortdesc>
+	    <content type="boolean"/>
+	</parameter>
+
 	<parameter name="fsid">
 	    <longdesc lang="en">
 	    	File system ID for NFS exports.  This can be overridden
@@ -279,9 +291,6 @@
 	gfs)
 		return $OCF_SUCCESS
 		;;
-	ocfs|ocfs2)
-		return $OCF_SUCCESS
-		;;
 	*)
 		ocf_log err "File system type $OCF_RESKEY_fstype not supported"
 		return $OCF_ERR_ARGS
@@ -798,6 +807,15 @@
 		esac
 	fi
 
+	if [ -n "$mp" ]; then
+		case ${OCF_RESKEY_self_fence} in
+	        $YES_STR)	self_fence=$YES ;;
+		1)		self_fence=$YES ;;
+	        *)		self_fence="" ;;
+		esac
+	fi
+
+
 	#
 	# Always do this hackery on clustered file systems.
 	#
@@ -873,8 +891,13 @@
 	done # while 
 
 	if [ -n "$umount_failed" ]; then
-		ocf_log err "'umount $dev' failed ($mp), error=$ret_val"
+		ocf_log err "'umount $mp' failed, error=$ret_val"
 
+		if [ "$self_fence" ]; then
+			ocf_log alert "umount failed - REBOOTING"
+			sync
+			reboot -fn
+		fi
 		return $FAIL
 	fi
 
@@ -884,8 +907,20 @@
 
 case $1 in
 start)
-	startFilesystem
-	exit $?
+	declare tries=0
+	declare rv
+
+	while [ $tries -lt 3 ]; do
+		startFilesystem
+		rv=$?
+		if [ rv -eq 0 ]; then
+			exit 0
+		fi
+
+		((tries++))
+		sleep 3
+	done
+	exit $rv
 	;;
 stop)
 	stopFilesystem
--- cluster/rgmanager/src/resources/fs.sh	2007/05/21 15:58:04	1.23
+++ cluster/rgmanager/src/resources/fs.sh	2007/11/30 20:06:55	1.24
@@ -535,8 +535,8 @@
 	do
 		#echo "spec=$1 dev=$dev  tmp_dev=$tmp_dev"
 		tmp_dev=$(real_device $tmp_dev)
-		tmp_mp=$(trim_trailing_slash $tmp_mp)
-		mp=$(trim_trailing_slash $mp)
+		tmp_mp=${tmp_mp/%\//}  #$(trim_trailing_slash $tmp_mp)
+		mp=${mp/%\//}		       #$(trim_trailing_slash $mp)
 
 		if [ -n "$tmp_dev" -a "$tmp_dev" = "$dev" ]; then
 			#
@@ -1149,6 +1149,9 @@
 			umount_failed=
 			done=$YES
 			;;
+		$FAIL)
+			return $FAIL
+			;;
 		$YES)
 			sync; sync; sync
 			ocf_log info "unmounting $mp"
--- cluster/rgmanager/src/resources/ocf-shellfuncs	2007/01/15 19:52:05	1.4
+++ cluster/rgmanager/src/resources/ocf-shellfuncs	2007/11/30 20:06:55	1.5
@@ -1,5 +1,5 @@
 #
-# 	$Id: ocf-shellfuncs,v 1.4 2007/01/15 19:52:05 lhh Exp $
+# 	$Id: ocf-shellfuncs,v 1.5 2007/11/30 20:06:55 lhh Exp $
 #
 # 	Common helper functions for the OCF Resource Agents supplied by
 # 	heartbeat.
@@ -174,6 +174,10 @@
 	esac
 
 	pretty_echo $__OCF_PRIO "$__OCF_MSG"
+
+	if [ -z "`which clulog 2> /dev/null`" ]; then
+		return 0
+	fi
 	clulog -p $__LOG_PID -n $__LOG_NAME \
 		-s $__OCF_PRIO_N "$__OCF_MSG"
 }
--- cluster/rgmanager/src/resources/service.sh	2007/07/31 18:00:25	1.11
+++ cluster/rgmanager/src/resources/service.sh	2007/11/30 20:06:55	1.12
@@ -77,7 +77,7 @@
             <shortdesc lang="en">
 	    	Automatic start after quorum formation
             </shortdesc>
-            <content type="boolean"/>
+            <content type="boolean" default="1"/>
         </parameter>
 
         <parameter name="hardrecovery" reconfig="1">
@@ -92,10 +92,10 @@
             <shortdesc lang="en">
 	    	Reboot if stop phase fails
             </shortdesc>
-            <content type="boolean"/>
+            <content type="boolean" default="0"/>
         </parameter>
 
-        <parameter name="exclusive">
+        <parameter name="exclusive" reconfig="1">
             <longdesc lang="en">
 	    	If set, this resource group will only relocate to
 		nodes which have no other resource groups running in the
@@ -109,7 +109,7 @@
             <shortdesc lang="en">
 	        Exclusive resource group
             </shortdesc>
-            <content type="boolean"/>
+            <content type="boolean" default="0"/>
         </parameter>
 
 	<parameter name="nfslock">
@@ -125,7 +125,7 @@
 	    <shortdesc lang="en">
 	        Enable NFS lock workarounds
 	    </shortdesc>
-	    <content type="boolean"/>
+	    <content type="boolean" default="0"/>
 	</parameter>
                 
         <parameter name="recovery" reconfig="1">
@@ -141,7 +141,7 @@
             <shortdesc lang="en">
 	    	Failure recovery policy
             </shortdesc>
-            <content type="string"/>
+            <content type="string" default="restart"/>
         </parameter>
 
         <parameter name="depend">
@@ -154,6 +154,32 @@
             </shortdesc>
             <content type="string"/>
         </parameter>
+
+        <parameter name="max_restarts">
+            <longdesc lang="en">
+	    	Maximum restarts for this service.
+            </longdesc>
+            <shortdesc lang="en">
+	    	Maximum restarts for this service.
+            </shortdesc>
+            <content type="string" default="0"/>
+        </parameter>
+
+        <parameter name="restart_expire_time">
+            <longdesc lang="en">
+	    	Restart expiration time
+            </longdesc>
+            <shortdesc lang="en">
+	    	Restart expiration time.  A restart is forgotten
+		after this time.  When combined with the max_restarts
+		option, this lets administrators specify a threshold
+		for when to fail over services.  If max_restarts
+		is exceeded in this given expiration time, the service
+		is relocated instead of restarted again.
+            </shortdesc>
+            <content type="string" default="0"/>
+        </parameter>
+
     </parameters>
 
     <actions>
@@ -229,8 +255,8 @@
 		exit 0
 		;;
 	reconfig)
-  		exit 0
-  		;;
+		exit 0
+		;;
 	*)
 		exit 0
 		;;
--- cluster/rgmanager/src/resources/vm.sh	2007/08/02 14:53:38	1.7
+++ cluster/rgmanager/src/resources/vm.sh	2007/11/30 20:06:55	1.8
@@ -77,7 +77,39 @@
             <shortdesc lang="en">
 	    	Automatic start after quorum formation
             </shortdesc>
-            <content type="boolean"/>
+            <content type="boolean" default="1"/>
+        </parameter>
+
+        <parameter name="hardrecovery" reconfig="1">
+            <longdesc lang="en">
+	    	If set to yes, the last owner will reboot if this resource
+		group fails to stop cleanly, thus allowing the resource
+		group to fail over to another node.  Use with caution; a
+		badly-behaved resource could cause the entire cluster to
+		reboot.  This should never be enabled if the automatic
+		start feature is used.
+            </longdesc>
+            <shortdesc lang="en">
+	    	Reboot if stop phase fails
+            </shortdesc>
+            <content type="boolean" default="0"/>
+        </parameter>
+
+        <parameter name="exclusive" reconfig="1">
+            <longdesc lang="en">
+	    	If set, this resource group will only relocate to
+		nodes which have no other resource groups running in the
+		event of a failure.  If no empty nodes are available,
+		this resource group will not be restarted after a failure.
+		Additionally, resource groups will not automatically
+		relocate to the node running this resource group.  This
+		option can be overridden by manual start and/or relocate
+		operations.
+            </longdesc>
+            <shortdesc lang="en">
+	        Exclusive resource group
+            </shortdesc>
+            <content type="boolean" default="0"/>
         </parameter>
 
         <parameter name="recovery" reconfig="1">
@@ -177,6 +209,51 @@
             <content type="string"/>
         </parameter>
 
+	<parameter name="migrate">
+	    <longdesc lang="en">
+	    	Migration type live or pause, default = live.
+	    </longdesc>
+	    <shortdesc lang="en">
+	    	Migration type live or pause, default = live.
+	    </shortdesc>
+            <content type="string" default="live"/>
+        </parameter>
+
+        <parameter name="depend">
+            <longdesc lang="en">
+		Top-level service this depends on, in "service:name"; format.
+            </longdesc>
+            <shortdesc lang="en">
+		Service dependency; will not start without the specified
+		service running.
+            </shortdesc>
+            <content type="string"/>
+        </parameter>
+
+        <parameter name="max_restarts" reconfig="1">
+            <longdesc lang="en">
+	    	Maximum restarts for this service.
+            </longdesc>
+            <shortdesc lang="en">
+	    	Maximum restarts for this service.
+            </shortdesc>
+            <content type="string" default="0"/>
+        </parameter>
+
+        <parameter name="restart_expire_time" reconfig="1">
+            <longdesc lang="en">
+	    	Restart expiration time
+            </longdesc>
+            <shortdesc lang="en">
+	    	Restart expiration time.  A restart is forgotten
+		after this time.  When combined with the max_restarts
+		option, this lets administrators specify a threshold
+		for when to fail over services.  If max_restarts
+		is exceeded in this given expiration time, the service
+		is relocated instead of restarted again.
+            </shortdesc>
+            <content type="string" default="0"/>
+        </parameter>
 
     </parameters>
 
@@ -202,11 +279,11 @@
     </actions>
     
     <special tag="rgmanager">
-     	<!-- Destroy_on_delete / init_on_add are currently only
- 	     supported for migratory resources (no children
- 	     and the 'migrate' action; see above.  Do not try this
- 	     with normal services -->
-	<attributes maxinstances="1" destroy_on_delete="0" init_on_add="0"/>
+    	<!-- Destroy_on_delete / init_on_add are currently only
+	     supported for migratory resources (no children
+	     and the 'migrate' action; see above.  Do not try this
+	     with normal services -->
+        <attributes maxinstances="1" destroy_on_delete="0" init_on_add="0"/>
     </special>
 </resource-agent>
 EOT
@@ -220,7 +297,7 @@
 	# controlled externally; the external monitoring app
 	# should.
 	#
-	declare cmdline="restart=\"never\""
+	declare cmdline="on_shutdown=\"destroy\" on_reboot=\"destroy\" on_crash=\"destroy\""
 	declare varp val temp
 
 	#
@@ -260,6 +337,8 @@
 		path)
 			cmdline="$cmdline --path=\"$val\""
 			;;
+		migrate)
+			;;
 		*)
 			cmdline="$cmdline $varp=\"$val\""
 			;;
@@ -285,7 +364,7 @@
 	#
 	declare cmdline
 
-	do_status && return 0
+	status && return 0
 
 	cmdline="`build_xm_cmdline`"
 
@@ -314,7 +393,7 @@
 		while [ $timeout -gt 0 ]; do
 			sleep 5
 			((timeout -= 5))
-			do_status || return 0
+			status || return 0
 			while read dom state; do
 				#
 				# State is "stopped".  Kill it.
@@ -355,45 +434,12 @@
 #
 do_status()
 {
-	declare line
-
-  	xm list $OCF_RESKEY_name &> /dev/null
- 	if [ $? -eq 0 ]; then
- 		return $OCF_SUCCESS
- 	fi
- 	xm list migrating-$OCF_RESKEY_name &> /dev/null
-	if [ $? -eq 1 ]; then
-		return $OCF_NOT_RUNNING
-	fi
-
-	return $OCF_ERR_GENERIC
-
-### NOT REACHED ###
-
-	# virsh doesn't handle migrating domains right now
-	# When this gets fixed, we need to revisit this status
-	# function.
-
-	line=$(virsh domstate $OCF_RESKEY_name)
-	if [ "$line" = "" ]; then
-		return $OCF_NOT_RUNNING
+	xm list $OCF_RESKEY_name &> /dev/null
+	if [ $? -eq 0 ]; then
+		return 0
 	fi
-
-	if [ "$line" = "blocked" ]; then
-		return $OCF_SUCCESS
-	elif [ "$line" = "running" ]; then
-		return $OCF_SUCCESS
-	elif [ "$line" = "in shutdown" ]; then
-		return $OCF_SUCCESS
-	elif [ "$line" = "shut off" ]; then
-		return $OCF_NOT_RUNNING
-	fi
-
-	#
-	# Crashed or paused
-	#
-
-	return $OCF_ERR_GENERIC
+	xm list migrating-$OCF_RESKEY_name &> /dev/null
+	return $?
 }
 
 
@@ -412,9 +458,13 @@
 migrate()
 {
 	declare target=$1
-	declare errstr rv
+	declare errstr rv migrate_opt
+
+	if [ "$OCF_RESKEY_migrate" = "live" ]; then
+		migrate_opt="-l"
+	fi
 	
-	err=$(xm migrate $OCF_RESKEY_name $target 2>&1 | head -1)
+	err=$(xm migrate $migrate_opt $OCF_RESKEY_name $target 2>&1 | head -1)
 	rv=$?
 
 	if [ $rv -ne 0 ]; then
@@ -446,7 +496,7 @@
 		exit $?
 		;;
 	kill)
-		do_stop destroy
+		stop destroy
 		exit $?
 		;;
 	recover|restart)
@@ -457,7 +507,7 @@
 		exit $?
 		;;
 	migrate)
-		do_migrate $2 # Send VM to this node
+		migrate $2 # Send VM to this node
 		exit $?
 		;;
 	reload)
@@ -478,6 +528,6 @@
 		;;
 	*)
 		echo "usage: $0 {start|stop|restart|status|reload|reconfig|meta-data|validate-all}"
-		exit $OCF_ERR_UNIMPLEMENTED
+		exit 1
 		;;
 esac
--- cluster/rgmanager/src/utils/clulog.c	2007/03/27 19:33:20	1.4
+++ cluster/rgmanager/src/utils/clulog.c	2007/11/30 20:06:55	1.5
@@ -92,9 +92,6 @@
     if (argc < 4)
 	usage(argv[0]);
 
-    /* ../daemons/log.c */
-    configure_logging(-1);
-
     while ((opt = getopt(argc, argv, "f:l:s:hp:n:")) != -1) {
 	switch (opt) {
 	case 'l':
@@ -133,9 +130,10 @@
     if (!cmdline_loglevel) {
 	/*
 	 * Let's see what loglevel the SM is running at.
-	 * TODO Get rgmgr log level
+	 * If ccsd's not available, use default.
 	 */
-	clu_set_loglevel(LOGLEVEL_DFLT);
+    	if (configure_logging(-1) < 0)
+		clu_set_loglevel(LOGLEVEL_DFLT);
     }
     result = clulog_pid(severity, pid, progname, logmsg);
     free(progname);
--- cluster/rgmanager/src/utils/clustat.c	2007/09/19 10:56:08	1.35
+++ cluster/rgmanager/src/utils/clustat.c	2007/11/30 20:06:55	1.36
@@ -21,6 +21,7 @@
 #define FLAG_RGMGR 0x4
 #define FLAG_NOCFG 0x8	/* Shouldn't happen */
 #define FLAG_QDISK 0x10
+#define FLAG_RGMAST 0x20 /* for RIND */
 
 #define RG_VERBOSE 0x1
 
@@ -30,6 +31,8 @@
 
 
 int running = 1;
+int dimx = 80, dimy = 24, stdout_is_tty = 0;
+int rgmanager_master_present = 0;
 
 void
 term_handler(int sig)
@@ -44,6 +47,28 @@
 } rg_state_list_t;
 
 
+int
+rg_name_sort(const void *left, const void *right)
+{
+	return strcmp(((rg_state_t *)left)->rs_name,
+		      ((rg_state_t *)right)->rs_name);
+}
+
+
+int
+member_id_sort(const void *left, const void *right)
+{
+	cman_node_t *l = (cman_node_t *)left;
+	cman_node_t *r = (cman_node_t *)right;
+
+	if (l->cn_nodeid < r->cn_nodeid)
+		return -1;
+	if (l->cn_nodeid > r->cn_nodeid)
+		return 1;
+	return 0;
+}
+
+
 void
 flag_rgmanager_nodes(cluster_member_list_t *cml)
 {
@@ -55,7 +80,7 @@
 	struct timeval tv;
 
 	if (msg_open(MSG_SOCKET, 0, 0, &ctx, 10) < 0) {
-		perror("msg_open");
+		//perror("msg_open");
 		return;
 	}
 
@@ -121,6 +146,10 @@
 			if (cml->cml_members[n].cn_nodeid != msgp->gh_arg1)
 				continue;
 			cml->cml_members[n].cn_member |= FLAG_RGMGR;
+			if (msgp->gh_arg2) {
+				rgmanager_master_present = 1;
+				cml->cml_members[n].cn_member |= FLAG_RGMAST;
+			}
 		}
 
 		free(msgp);
@@ -147,7 +176,7 @@
 	struct timeval tv;
 
 	if (msg_open(MSG_SOCKET, 0, 0, &ctx, 10) < 0) {
-		perror("msg_open");
+		//perror("msg_open");
 		return NULL;
 	}
 
@@ -248,6 +277,9 @@
 		return NULL;
 	}
 
+	qsort(rsl->rgl_states, rsl->rgl_count, sizeof(rg_state_t),
+	      rg_name_sort);
+
 	return rsl;
 }
 
@@ -270,9 +302,11 @@
 		sleep(1);
 	
 	x = 0;
+	memset(buf, 0, sizeof(buf));
+
 	while (++x) {
 		name = NULL;
-		snprintf(buf, sizeof(buf),
+		snprintf(buf, sizeof(buf)-1,
 			"/cluster/clusternodes/clusternode[%d]/@name", x);
 
 		if (ccs_get(desc, buf, &name) != 0)
@@ -307,7 +341,7 @@
 		free(name);
 
 		/* Add node ID */
-		snprintf(buf, sizeof(buf),
+		snprintf(buf, sizeof(buf)-1,
 			 "/cluster/clusternodes/clusternode[%d]/@nodeid", x);
 		if (ccs_get(desc, buf, &name) == 0) {
 			nodes[x-1].cn_nodeid = atoi(name);
@@ -320,6 +354,9 @@
 	ccs_disconnect(desc);
 	ret->cml_members = nodes;
 
+	qsort(ret->cml_members, ret->cml_count, sizeof(cman_node_t),
+	      member_id_sort);
+
 	return ret;
 }
 
@@ -413,68 +450,71 @@
 
 
 void
-_txt_rg_state(rg_state_t *rs, cluster_member_list_t *members, int flags)
+_txt_rg_state(rg_state_t *rs, cluster_member_list_t *members, int flags,
+	      char *fmt_buf, int ns)
 {
-	char owner[31];
-	char flags_string[255] = "";
+	char owner[MAXHOSTNAMELEN+1];
+	char owner_fmt[16];
+	char *name = rs->rs_name, *ptr;
+	int l;
+
+	if (stdout_is_tty) {
+		ptr = strchr(rs->rs_name, ':');
+		if (ptr) {
+			l = (int)(ptr - rs->rs_name);
+			if ((l == 7) &&  /* strlen("service") == 7 */
+			    (strncmp(rs->rs_name, "service", l) == 0)) 
+				name = ptr+1;
+		}
+	}
+
+	memset(owner, 0, sizeof(owner));
+	memset(owner_fmt, 0, sizeof(owner_fmt));
 
 	if (rs->rs_state == RG_STATE_STOPPED ||
 	    rs->rs_state == RG_STATE_DISABLED ||
 	    rs->rs_state == RG_STATE_ERROR ||
 	    rs->rs_state == RG_STATE_FAILED) {
 
-		snprintf(owner, sizeof(owner), "(%-.28s)",
+		snprintf(owner_fmt, sizeof(owner_fmt)-1, "(%%-.%ds)", ns-2);
+		snprintf(owner, sizeof(owner)-1, owner_fmt,
 			 my_memb_id_to_name(members, rs->rs_last_owner));
 	} else {
 
-		snprintf(owner, sizeof(owner), "%-.30s",
+		snprintf(owner_fmt, sizeof(owner_fmt)-1, "%%-.%ds", ns);
+		snprintf(owner, sizeof(owner)-1, owner_fmt,
 			 my_memb_id_to_name(members, rs->rs_owner));
 	}
-	rg_flags_str(flags_string, sizeof(flags_string), rs->rs_flags, ", ");
-	printf("  %-20.20s %-30.30s %-16.16s ",
-	       rs->rs_name,
+	
+	printf(fmt_buf,
+	       name,
 	       owner,
 	       rg_state_str(rs->rs_state));
-	if(strlen(flags_string))
-		printf ("%-30.30s\n", flags_string);
-	else
-		printf("\n");
 }
 
 
 void
 _txt_rg_state_v(rg_state_t *rs, cluster_member_list_t *members, int flags)
 {
-	char flags_string[255] = "";
-	time_t transtime = rs->rs_transition;
-
-	rg_flags_str(flags_string, sizeof(flags_string), rs->rs_flags, ", ");
-
 	printf("Service Name      : %s\n", rs->rs_name);
 	printf("  Current State   : %s (%d)\n",
 	       rg_state_str(rs->rs_state), rs->rs_state);
-	if (rs->rs_flags)
-		printf("  Flags           : %s (%d)\n",
-		       flags_string, rs->rs_flags);
-	else
-		printf("  Flags           : none (%d)\n",
-		       rs->rs_flags);
 	printf("  Owner           : %s\n",
 	       my_memb_id_to_name(members, rs->rs_owner));
 	printf("  Last Owner      : %s\n",
 	       my_memb_id_to_name(members, rs->rs_last_owner));
 	printf("  Last Transition : %s\n",
-	       ctime(&transtime));
+	       ctime((time_t *)(&rs->rs_transition)));
 }
 
 
 void
-txt_rg_state(rg_state_t *rs, cluster_member_list_t *members, int flags)
+txt_rg_state(rg_state_t *rs, cluster_member_list_t *members, int flags, char *fmt_buf, int ns)
 {
 	if (flags & RG_VERBOSE) 
 		_txt_rg_state_v(rs, members, flags);
 	else
-		_txt_rg_state(rs, members, flags);
+		_txt_rg_state(rs, members, flags, fmt_buf, ns);
 }
 
 
@@ -482,12 +522,10 @@
 xml_rg_state(rg_state_t *rs, cluster_member_list_t *members, int flags)
 {
 	char time_str[32];
-	char flags_string[255] = "";
-	time_t transtime = rs->rs_transition;
 	int x;
 
 	/* Chop off newlines */
-	ctime_r((time_t *)&transtime, time_str);
+	ctime_r((time_t *)&rs->rs_transition, time_str);
 	for (x = 0; time_str[x]; x++) {
 		if (time_str[x] < 32) {
 			time_str[x] = 0;
@@ -495,15 +533,12 @@
 		}
 	}
 
-	printf("    <group name=\"%s\" state=\"%d\" state_str=\"%s\""
-	       " flags=\"%d\" flags_str=\"%s\""
+	printf("    <group name=\"%s\" state=\"%d\" state_str=\"%s\" "
 	       " owner=\"%s\" last_owner=\"%s\" restarts=\"%d\""
 	       " last_transition=\"%llu\" last_transition_str=\"%s\"/>\n",
 	       rs->rs_name,
 	       rs->rs_state,
 	       rg_state_str(rs->rs_state),
-	       rs->rs_flags,
-	       rg_flags_str(flags_string, sizeof(flags_string), rs->rs_flags, " "),
 	       my_memb_id_to_name(members, rs->rs_owner),
 	       my_memb_id_to_name(members, rs->rs_last_owner),
 	       rs->rs_restarts,
@@ -512,11 +547,37 @@
 }
 
 
+void
+build_service_format(char *buf, int buflen, int cols, int *ns)
+{
+	/* Based on 80 columns */
+	int svcsize = 30;
+	int nodesize = 30;
+	int statsize = 14;	/* uninitialized */
+	int pad = 6;		/* Spaces and such; newline */
+
+	svcsize = (cols - (statsize + pad)) / 2;
+	nodesize = (cols - (statsize + pad)) / 2;
+	if (svcsize > MAXHOSTNAMELEN)
+		svcsize = MAXHOSTNAMELEN;
+	if (nodesize > MAXHOSTNAMELEN)
+		nodesize = MAXHOSTNAMELEN;
+
+	memset(buf, 0, buflen);
+	snprintf(buf, buflen-1, "  %%-%d.%ds %%-%d.%ds %%-%d.%ds\n",
+		 svcsize, svcsize, nodesize, nodesize, statsize,
+		 statsize);
+
+	*ns = nodesize;
+}
+
+
 int
 txt_rg_states(rg_state_list_t *rgl, cluster_member_list_t *members, 
 	      char *svcname, int flags)
 {
-	int x, ret = 0;
+	int x, ret = 0, ns;
+	char fmt_buf[80];
 
 	if (!rgl || !members)
 		return -1;
@@ -524,11 +585,14 @@
 	if (svcname)
 		ret = -1;
 
+	build_service_format(fmt_buf, sizeof(fmt_buf), dimx, &ns);
+
 	if (!(flags & RG_VERBOSE)) {
-		printf("  %-20.20s %-30.30s %-16.16s %-30.30s\n",
-		       "Service Name", "Owner (Last)", "State", "Flags");
-		printf("  %-20.20s %-30.30s %-16.16s %-30.30s\n",
-		       "------- ----", "----- ------", "-----", "-----");
+
+		printf(fmt_buf,
+		       "Service Name", "Owner (Last)", "State");
+		printf(fmt_buf,
+		       "------- ----", "----- ------", "-----");
 	} else {
 		printf("Service Information\n"
 		       "------- -----------\n\n");
@@ -538,7 +602,7 @@
 		if (svcname &&
 		    strcmp(rgl->rgl_states[x].rs_name, svcname))
 			continue;
-		txt_rg_state(&rgl->rgl_states[x], members, flags);
+		txt_rg_state(&rgl->rgl_states[x], members, flags, fmt_buf, ns);
 		if (svcname) {
 			switch (rgl->rgl_states[x].rs_state) {
 			case RG_STATE_STARTING:
@@ -551,7 +615,7 @@
 			}
 		}
 	}
-	
+
 	return ret;
 }
 
@@ -604,6 +668,24 @@
 
 
 void
+txt_cluster_info(cman_cluster_t *ci) 
+{
+	time_t now = time(NULL);
+
+	printf("Cluster Status for %s @ %s",
+	       ci->ci_name, ctime(&now));
+}
+
+
+void
+xml_cluster_info(cman_cluster_t *ci) 
+{
+	printf("  <cluster name=\"%s\" id=\"%d\" generation=\"%d\"/>\n",
+	       ci->ci_name, ci->ci_number, ci->ci_generation);
+}
+
+
+void
 xml_quorum_state(int qs)
 {
 	/* XXX output groupmember attr (carry over from RHCS4) */
@@ -619,15 +701,31 @@
 	} else {
 		printf(" groupmember=\"0\"");
 	}
+
 	printf("/>\n");
 }
 
+void
+build_member_format(char *buf, int buflen, int cols)
+{
+	/* Based on 80 columns */
+	int nodesize = 40;
+
+	nodesize = (cols / 2);
+	if (nodesize > MAXHOSTNAMELEN)
+		nodesize = MAXHOSTNAMELEN;
+
+	memset(buf, 0, buflen);
+	snprintf(buf, buflen-1, "  %%-%d.%ds ",
+		 nodesize, nodesize);
+}
+
 
 void
-txt_member_state(cman_node_t *node)
+txt_member_state(cman_node_t *node, char *fmt_buf)
 {
-	printf("  %-34.34s %4d ", node->cn_name,
-	       node->cn_nodeid);
+	printf(fmt_buf, node->cn_name);
+	printf("%4d ", node->cn_nodeid);
 
 	if (node->cn_member & FLAG_UP)
 		printf("Online");
@@ -640,15 +738,21 @@
 	if (node->cn_member & FLAG_NOCFG)
 		printf(", Estranged");
 	
-	if (node->cn_member & FLAG_RGMGR)
-		printf(", rgmanager");
+	if (node->cn_member & FLAG_RGMGR) {
+		if (rgmanager_master_present) {
+			if (node->cn_member & FLAG_RGMAST) 
+				printf(", RG-Master");
+			else
+				printf(", RG-Worker");
+		} else {
+			printf(", rgmanager");
+		}
+	}
 	
 	if (node->cn_member & FLAG_QDISK)
 		printf(", Quorum Disk");
 
 	printf("\n");
-		
-
 }
 
 
@@ -656,12 +760,14 @@
 xml_member_state(cman_node_t *node)
 {
 	printf("    <node name=\"%s\" state=\"%d\" local=\"%d\" "
-	       "estranged=\"%d\" rgmanager=\"%d\" qdisk=\"%d\" nodeid=\"0x%08x\"/>\n",
+	       "estranged=\"%d\" rgmanager=\"%d\" rgmanager_master=\"%d\" "
+	       "qdisk=\"%d\" nodeid=\"0x%08x\"/>\n",
 	       node->cn_name,
 	       !!(node->cn_member & FLAG_UP),
 	       !!(node->cn_member & FLAG_LOCAL),
 	       !!(node->cn_member & FLAG_NOCFG),
 	       !!(node->cn_member & FLAG_RGMGR),
+	       !!(node->cn_member & FLAG_RGMAST),
 	       !!(node->cn_member & FLAG_QDISK),
 	       (uint32_t)((node->cn_nodeid      )&0xffffffff));
 }
@@ -670,6 +776,7 @@
 int
 txt_member_states(cluster_member_list_t *membership, char *name)
 {
+	char buf[80];
 	int x, ret = 0;
 
   	if (!membership) {
@@ -677,13 +784,17 @@
  		return -1;
   	}
 
-	printf("  %-34.34s %-4.4s %s\n", "Member Name", "ID", "Status");
-	printf("  %-34.34s %-4.4s %s\n", "------ ----", "----", "------");
+	build_member_format(buf, sizeof(buf), dimx);
+
+	printf(buf, "Member Name");
+	printf("%-4.4s %s\n", "ID", "Status");
+	printf(buf, "------ ----");
+	printf("%-4.4s %s\n", "----", "------");
 
 	for (x = 0; x < membership->cml_count; x++) {
 		if (name && strcmp(membership->cml_members[x].cn_name, name))
 			continue;
-		txt_member_state(&membership->cml_members[x]);
+		txt_member_state(&membership->cml_members[x], buf);
  		ret = !(membership->cml_members[x].cn_member & FLAG_UP);
 	}
 
@@ -717,13 +828,15 @@
 
 
 int 
-txt_cluster_status(int qs, cluster_member_list_t *membership,
+txt_cluster_status(cman_cluster_t *ci,
+		   int qs, cluster_member_list_t *membership,
 		   rg_state_list_t *rgs, char *name, char *svcname, 
 		   int flags)
 {
 	int ret;
 	
 	if (!svcname && !name) {
+  		txt_cluster_info(ci);
 		txt_quorum_state(qs);
 		if (!membership) {
 			/* XXX Check for rgmanager?! */
@@ -738,12 +851,14 @@
  		return ret;
  	if (!name || (name && svcname))
  		ret = txt_rg_states(rgs, membership, svcname, flags);
+
  	return ret;
 }
 
 
 int
-xml_cluster_status(int qs, cluster_member_list_t *membership,
+xml_cluster_status(cman_cluster_t *ci, int qs,
+		   cluster_member_list_t *membership,
 		   rg_state_list_t *rgs, char *name, char *svcname,
 		   int flags)
 {
@@ -768,6 +883,8 @@
 	}
 
   	if (!svcname && !name)
+  		xml_cluster_info(ci);
+  	if (!svcname && !name)
   		xml_quorum_state(qs);
   	if (!svcname || (name && svcname)) 
  		ret1 = xml_member_states(membership, name);
@@ -862,7 +979,9 @@
 	int local_node_id;
 	int fast = 0;
 	int runtype = 0;
+	time_t now;
 	cman_handle_t ch = NULL;
+	cman_cluster_t ci;
 
 	int refresh_sec = 0, errors = 0;
 	int opt, xml = 0, flags = 0;
@@ -900,8 +1019,9 @@
 		case 's':
 			rg_name = optarg;
 			if (!strchr(rg_name,':')) {
+				memset(real_rg_name, 0, sizeof(real_rg_name));
 				snprintf(real_rg_name,
-					 sizeof(real_rg_name),
+					 sizeof(real_rg_name)-1,
 					 "service:%s";, rg_name);
 				rg_name = real_rg_name;
 			}
@@ -941,7 +1061,7 @@
 	/* Connect & grab all our info */
 	ch = cman_init(NULL);
 	if (!ch) {
-		printf("CMAN is not running.\n");
+		perror("Could not connect to CMAN");
 		return 1;
 	}
 
@@ -952,8 +1072,12 @@
 		ret = !(cman_is_quorate(ch));
 		goto cleanup;
 	case VERSION_ONLY:
+#ifdef RELEASE_VERSION
 		printf("%s version %s\n", basename(argv[0]),
 		       RELEASE_VERSION);
+#else
+		printf("%s version DEVEL\n", basename(argv[0]));
+#endif
 		if (!ch)
 		       break;
 		goto cleanup;
@@ -974,6 +1098,16 @@
 	signal(SIGINT, term_handler);
 	signal(SIGTERM, term_handler);
 
+	if (isatty(STDOUT_FILENO)) {
+		stdout_is_tty = 1;
+		setupterm((char *) 0, STDOUT_FILENO, (int *) 0);
+		dimx = tigetnum("cols");
+		dimy = tigetnum("lines");
+	}
+
+	memset(&ci, 0, sizeof(ci));
+	cman_get_cluster(ch, &ci);
+
 	while (1) {
 		qs = cman_is_quorate(ch);
 		membership = build_member_list(ch, &local_node_id);
@@ -985,16 +1119,16 @@
 		}
 
 		if (refresh_sec) {
-			setupterm((char *) 0, STDOUT_FILENO, (int *) 0);
 			tputs(clear_screen, lines > 0 ? lines : 1, putchar);
+			now = time(NULL);
 		}
 
 		if (xml)
-			ret = xml_cluster_status(qs, membership, rgs,
+			ret = xml_cluster_status(&ci, qs, membership, rgs,
 						 member_name, rg_name,
 						 flags);
 		else
-			ret = txt_cluster_status(qs, membership, rgs,
+			ret = txt_cluster_status(&ci, qs, membership, rgs,
 						 member_name, rg_name,
 						 flags);
 
@@ -1011,5 +1145,6 @@
 
 cleanup:
 	cman_finish(ch);
+
 	return ret;
 }
--- cluster/rgmanager/src/utils/clusvcadm.c	2007/08/22 08:58:47	1.22
+++ cluster/rgmanager/src/utils/clusvcadm.c	2007/11/30 20:06:55	1.23
@@ -311,7 +311,11 @@
 			node_specified = 1;
 			break;
 		case 'v':
-			printf("%s\n",RELEASE_VERSION);
+#ifdef RELEASE_VERSION
+			printf("%s\n", RELEASE_VERSION);
+#else
+			printf("DEVEL\n");
+#endif
 			return 0;
 		case 'Z':
 			actionstr = "freezing";


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]