1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
|
# (c) Copyright IBM Corp. 2020 All Rights Reserved
#
# Author: Aman Kumar Sinha <amansi26@in.ibm.com>
#
# This file is part of cloud-init. See LICENSE file for license information.
"""
Reset RMC
------------
**Summary:** reset rsct node id
Reset RMC module is IBM PowerVM Hypervisor specific
Reliable Scalable Cluster Technology (RSCT) is a set of software components,
that together provide a comprehensive clustering environment (RAS features)
for IBM PowerVM based virtual machines. RSCT includes the Resource monitoring
and control (RMC) subsystem. RMC is a generalized framework used for managing,
monitoring, and manipulating resources. RMC runs as a daemon process on
individual machines and needs creation of unique node id and restarts
during VM boot.
More details refer
https://www.ibm.com/support/knowledgecenter/en/SGVKBA_3.2/admin/bl503_ovrv.htm
This module handles
- creation of the unique RSCT node id to every instance/virtual machine
and ensure once set, it isn't changed subsequently by cloud-init.
In order to do so, it restarts RSCT service.
Prerequisite of using this module is to install RSCT packages.
**Internal name:** ``cc_reset_rmc``
**Module frequency:** per instance
**Supported distros:** rhel, sles and ubuntu
"""
import os
from cloudinit import log as logging
from cloudinit.settings import PER_INSTANCE
from cloudinit import util
from cloudinit import subp
frequency = PER_INSTANCE
# RMCCTRL is expected to be in system PATH (/opt/rsct/bin)
# The symlink for RMCCTRL and RECFGCT are
# /usr/sbin/rsct/bin/rmcctrl and
# /usr/sbin/rsct/install/bin/recfgct respectively.
RSCT_PATH = '/opt/rsct/install/bin'
RMCCTRL = 'rmcctrl'
RECFGCT = 'recfgct'
LOG = logging.getLogger(__name__)
NODE_ID_FILE = '/etc/ct_node_id'
def handle(name, _cfg, cloud, _log, _args):
# Ensuring node id has to be generated only once during first boot
if cloud.datasource.platform_type == 'none':
LOG.debug('Skipping creation of new ct_node_id node')
return
if not os.path.isdir(RSCT_PATH):
LOG.debug("module disabled, RSCT_PATH not present")
return
orig_path = os.environ.get('PATH')
try:
add_path(orig_path)
reset_rmc()
finally:
if orig_path:
os.environ['PATH'] = orig_path
else:
del os.environ['PATH']
def reconfigure_rsct_subsystems():
# Reconfigure the RSCT subsystems, which includes removing all RSCT data
# under the /var/ct directory, generating a new node ID, and making it
# appear as if the RSCT components were just installed
try:
out = subp.subp([RECFGCT])[0]
LOG.debug(out.strip())
return out
except subp.ProcessExecutionError:
util.logexc(LOG, 'Failed to reconfigure the RSCT subsystems.')
raise
def get_node_id():
try:
fp = util.load_file(NODE_ID_FILE)
node_id = fp.split('\n')[0]
return node_id
except Exception:
util.logexc(LOG, 'Failed to get node ID from file %s.' % NODE_ID_FILE)
raise
def add_path(orig_path):
# Adding the RSCT_PATH to env standard path
# So thet cloud init automatically find and
# run RECFGCT to create new node_id.
suff = ":" + orig_path if orig_path else ""
os.environ['PATH'] = RSCT_PATH + suff
return os.environ['PATH']
def rmcctrl():
# Stop the RMC subsystem and all resource managers so that we can make
# some changes to it
try:
return subp.subp([RMCCTRL, '-z'])
except Exception:
util.logexc(LOG, 'Failed to stop the RMC subsystem.')
raise
def reset_rmc():
LOG.debug('Attempting to reset RMC.')
node_id_before = get_node_id()
LOG.debug('Node ID at beginning of module: %s', node_id_before)
# Stop the RMC subsystem and all resource managers so that we can make
# some changes to it
rmcctrl()
reconfigure_rsct_subsystems()
node_id_after = get_node_id()
LOG.debug('Node ID at end of module: %s', node_id_after)
# Check if new node ID is generated or not
# by comparing old and new node ID
if node_id_after == node_id_before:
msg = 'New node ID did not get generated.'
LOG.error(msg)
raise Exception(msg)
|