Repository URL to install this package:
Version:
3.3.14 ▾
|
tvault-contego
/
home
/
tvault
/
.virtenv
/
lib
/
python2.7
/
site-packages
/
smutLayer
/
changeVM.py
|
---|
# ChangeVM functions for Systems Management Ultra Thin Layer
#
# Copyright 2017 IBM Corp.
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
import os.path
import re
import shutil
import tarfile
import tempfile
from smutLayer import generalUtils
from smutLayer import msgs
from smutLayer.vmUtils import disableEnableDisk, execCmdThruIUCV, installFS
from smutLayer.vmUtils import invokeSMCLI, isLoggedOn
from smutLayer.vmUtils import punch2reader, purgeReader
modId = "CVM"
version = "1.0.0"
"""
List of subfunction handlers.
Each subfunction contains a list that has:
Readable name of the routine that handles the subfunction,
Code for the function call.
"""
subfuncHandler = {
'ADD3390': ['add3390', lambda rh: add3390(rh)],
'ADD9336': ['add9336', lambda rh: add9336(rh)],
'DEDICATE': ['dedicate', lambda rh: dedicate(rh)],
'UNDEDICATE': ['undedicate', lambda rh: undedicate(rh)],
'AEMOD': ['addAEMOD', lambda rh: addAEMOD(rh)],
'IPL': ['addIPL', lambda rh: addIPL(rh)],
'LOADDEV': ['addLOADDEV', lambda rh: addLOADDEV(rh)],
'HELP': ['help', lambda rh: help(rh)],
'PUNCHFILE': ['punchFile', lambda rh: punchFile(rh)],
'PURGERDR': ['purgeRDR', lambda rh: purgeRDR(rh)],
'REMOVEDISK': ['removeDisk', lambda rh: removeDisk(rh)],
'REMOVEIPL': ['removeIPL', lambda rh: removeIPL(rh)],
'VERSION': ['getVersion', lambda rh: getVersion(rh)],
}
"""
List of positional operands based on subfunction.
Each subfunction contains a list which has a dictionary with the following
information for the positional operands:
- Human readable name of the operand,
- Property in the parms dictionary to hold the value,
- Is it required (True) or optional (False),
- Type of data (1: int, 2: string).
"""
posOpsList = {
'ADD3390': [
['Disk pool name', 'diskPool', True, 2],
['Virtual address', 'vaddr', True, 2],
['Disk size', 'diskSize', True, 2]],
'ADD9336': [
['Disk pool name', 'diskPool', True, 2],
['Virtual address', 'vaddr', True, 2],
['Disk size', 'diskSize', True, 2]],
'DEDICATE': [
['Virtual device address', 'vaddr', True, 2],
['Real device address', 'raddr', True, 2],
['Read only mode', 'mode', True, 2]],
'UNDEDICATE': [
['Virtual device address', 'vaddr', True, 2]],
'AEMOD': [
['Activation Engine Modification Script',
'aeScript', True, 2]],
'IPL': [
['Virtual Address or NSS name', 'addrOrNSS', True, 2]],
'PUNCHFILE': [
['File to punch', 'file', True, 2]],
'REMOVEDISK': [
['Virtual address', 'vaddr', True, 2]],
'REMOVEIPL': [],
}
"""
List of additional operands/options supported by the various subfunctions.
The dictionary following the subfunction name uses the keyword from the
command as a key. Each keyword has a dictionary that lists:
- the related parms item that stores the value,
- how many values follow the keyword, and
- the type of data for those values (1: int, 2: string)
"""
keyOpsList = {
'ADD3390': {
'--filesystem': ['fileSystem', 1, 2],
'--mode': ['mode', 1, 2],
'--multipw': ['multiPW', 1, 2],
'--readpw': ['readPW', 1, 2],
'--showparms': ['showParms', 0, 0],
'--writepw': ['writePW', 1, 2]},
'ADD9336': {
'--filesystem': ['fileSystem', 1, 2],
'--mode': ['mode', 1, 2],
'--multipw': ['multiPW', 1, 2],
'--readpw': ['readPW', 1, 2],
'--showparms': ['showParms', 0, 0],
'--writepw': ['writePW', 1, 2]},
'AEMOD': {
'--invparms': ['invParms', 1, 2],
'--showparms': ['showParms', 0, 0]},
'HELP': {},
'IPL': {
'--loadparms': ['loadParms', 1, 2],
'--parms': ['parms', 1, 2],
'--showparms': ['showParms', 0, 0]},
'LOADDEV': {
'--boot': ['boot', 1, 2],
'--addr': ['addr', 1, 2],
'--lun': ['lun', 1, 2],
'--wwpn': ['wwpn', 1, 2],
'--scpDataType': ['scpDataType', 1, 2],
'--scpData': ['scpData', 1, 2],
'--showparms': ['showParms', 0, 0]},
'PUNCHFILE': {
'--class': ['class', 1, 2],
'--showparms': ['showParms', 0, 0], },
'PURGERDR': {'--showparms': ['showParms', 0, 0]},
'REMOVEDISK': {'--showparms': ['showParms', 0, 0]},
'REMOVEIPL': {'--showparms': ['showParms', 0, 0]},
'VERSION': {},
}
def add3390(rh):
"""
Adds a 3390 (ECKD) disk to a virtual machine's directory entry.
Input:
Request Handle with the following properties:
function - 'CHANGEVM'
subfunction - 'ADD3390'
userid - userid of the virtual machine
parms['diskPool'] - Disk pool
parms['diskSize'] - size of the disk in cylinders or bytes.
parms['fileSystem'] - Linux filesystem to install on the disk.
parms['mode'] - Disk access mode
parms['multiPW'] - Multi-write password
parms['readPW'] - Read password
parms['vaddr'] - Virtual address
parms['writePW'] - Write password
Output:
Request Handle updated with the results.
Return code - 0: ok, non-zero: error
"""
rh.printSysLog("Enter changeVM.add3390")
results, cyl = generalUtils.cvtToCyl(rh, rh.parms['diskSize'])
if results['overallRC'] != 0:
# message already sent. Only need to update the final results.
rh.updateResults(results)
if results['overallRC'] == 0:
parms = [
"-T", rh.userid,
"-v", rh.parms['vaddr'],
"-t", "3390",
"-a", "AUTOG",
"-r", rh.parms['diskPool'],
"-u", "1",
"-z", cyl,
"-f", "1"]
hideList = []
if 'mode' in rh.parms:
parms.extend(["-m", rh.parms['mode']])
else:
parms.extend(["-m", 'W'])
if 'readPW' in rh.parms:
parms.extend(["-R", rh.parms['readPW']])
hideList.append(len(parms) - 1)
if 'writePW' in rh.parms:
parms.extend(["-W", rh.parms['writePW']])
hideList.append(len(parms) - 1)
if 'multiPW' in rh.parms:
parms.extend(["-M", rh.parms['multiPW']])
hideList.append(len(parms) - 1)
results = invokeSMCLI(rh,
"Image_Disk_Create_DM",
parms,
hideInLog=hideList)
if results['overallRC'] != 0:
# SMAPI API failed.
rh.printLn("ES", results['response'])
rh.updateResults(results) # Use results returned by invokeSMCLI
if (results['overallRC'] == 0 and 'fileSystem' in rh.parms):
results = installFS(
rh,
rh.parms['vaddr'],
rh.parms['mode'],
rh.parms['fileSystem'],
"3390")
if results['overallRC'] == 0:
results = isLoggedOn(rh, rh.userid)
if results['overallRC'] != 0:
# Cannot determine if VM is logged on or off.
# We have partially failed. Pass back the results.
rh.updateResults(results)
elif results['rs'] == 0:
# Add the disk to the active configuration.
parms = [
"-T", rh.userid,
"-v", rh.parms['vaddr'],
"-m", rh.parms['mode']]
results = invokeSMCLI(rh, "Image_Disk_Create", parms)
if results['overallRC'] == 0:
rh.printLn("N", "Added dasd " + rh.parms['vaddr'] +
" to the active configuration.")
else:
# SMAPI API failed.
rh.printLn("ES", results['response'])
rh.updateResults(results) # Use results from invokeSMCLI
rh.printSysLog("Exit changeVM.add3390, rc: " +
str(rh.results['overallRC']))
return rh.results['overallRC']
def add9336(rh):
"""
Adds a 9336 (FBA) disk to virtual machine's directory entry.
Input:
Request Handle with the following properties:
function - 'CHANGEVM'
subfunction - 'ADD9336'
userid - userid of the virtual machine
parms['diskPool'] - Disk pool
parms['diskSize'] - size of the disk in blocks or bytes.
parms['fileSystem'] - Linux filesystem to install on the disk.
parms['mode'] - Disk access mode
parms['multiPW'] - Multi-write password
parms['readPW'] - Read password
parms['vaddr'] - Virtual address
parms['writePW'] - Write password
Output:
Request Handle updated with the results.
Return code - 0: ok, non-zero: error
"""
rh.printSysLog("Enter changeVM.add9336")
results, blocks = generalUtils.cvtToBlocks(rh, rh.parms['diskSize'])
if results['overallRC'] != 0:
# message already sent. Only need to update the final results.
rh.updateResults(results)
if results['overallRC'] == 0:
parms = [
"-T", rh.userid,
"-v", rh.parms['vaddr'],
"-t", "9336",
"-a", "AUTOG",
"-r", rh.parms['diskPool'],
"-u", "1",
"-z", blocks,
"-f", "1"]
hideList = []
if 'mode' in rh.parms:
parms.extend(["-m", rh.parms['mode']])
else:
parms.extend(["-m", 'W'])
if 'readPW' in rh.parms:
parms.extend(["-R", rh.parms['readPW']])
hideList.append(len(parms) - 1)
if 'writePW' in rh.parms:
parms.extend(["-W", rh.parms['writePW']])
hideList.append(len(parms) - 1)
if 'multiPW' in rh.parms:
parms.extend(["-M", rh.parms['multiPW']])
hideList.append(len(parms) - 1)
results = invokeSMCLI(rh,
"Image_Disk_Create_DM",
parms,
hideInLog=hideList)
if results['overallRC'] != 0:
# SMAPI API failed.
rh.printLn("ES", results['response'])
rh.updateResults(results) # Use results from invokeSMCLI
if (results['overallRC'] == 0 and 'fileSystem' in rh.parms):
# Install the file system
results = installFS(
rh,
rh.parms['vaddr'],
rh.parms['mode'],
rh.parms['fileSystem'],
"9336")
if results['overallRC'] == 0:
results = isLoggedOn(rh, rh.userid)
if (results['overallRC'] == 0 and results['rs'] == 0):
# Add the disk to the active configuration.
parms = [
"-T", rh.userid,
"-v", rh.parms['vaddr'],
"-m", rh.parms['mode']]
results = invokeSMCLI(rh, "Image_Disk_Create", parms)
if results['overallRC'] == 0:
rh.printLn("N", "Added dasd " + rh.parms['vaddr'] +
" to the active configuration.")
else:
# SMAPI API failed.
rh.printLn("ES", results['response'])
rh.updateResults(results) # Use results from invokeSMCLI
rh.printSysLog("Exit changeVM.add9336, rc: " +
str(rh.results['overallRC']))
return rh.results['overallRC']
def dedicate(rh):
"""
Dedicate device.
Input:
Request Handle with the following properties:
function - 'CHANGEVM'
subfunction - 'DEDICATEDM'
userid - userid of the virtual machine
parms['vaddr'] - Virtual address
parms['raddr'] - Real address
parms['mode'] - Read only mode or not.
Output:
Request Handle updated with the results.
Return code - 0: ok, non-zero: error
"""
rh.printSysLog("Enter changeVM.dedicate")
parms = [
"-T", rh.userid,
"-v", rh.parms['vaddr'],
"-r", rh.parms['raddr'],
"-R", rh.parms['mode']]
hideList = []
results = invokeSMCLI(rh,
"Image_Device_Dedicate_DM",
parms,
hideInLog=hideList)
if results['overallRC'] != 0:
# SMAPI API failed.
rh.printLn("ES", results['response'])
rh.updateResults(results) # Use results from invokeSMCLI
if results['overallRC'] == 0:
results = isLoggedOn(rh, rh.userid)
if (results['overallRC'] == 0 and results['rs'] == 0):
# Dedicate device to active configuration.
parms = [
"-T", rh.userid,
"-v", rh.parms['vaddr'],
"-r", rh.parms['raddr'],
"-R", rh.parms['mode']]
results = invokeSMCLI(rh, "Image_Device_Dedicate", parms)
if results['overallRC'] == 0:
rh.printLn("N", "Dedicated device " + rh.parms['vaddr'] +
" to the active configuration.")
else:
# SMAPI API failed.
rh.printLn("ES", results['response'])
rh.updateResults(results) # Use results from invokeSMCLI
rh.printSysLog("Exit changeVM.dedicate, rc: " +
str(rh.results['overallRC']))
return rh.results['overallRC']
def undedicate(rh):
"""
Unedicate device.
Input:
Request Handle with the following properties:
function - 'CHANGEVM'
subfunction - 'UNDEDICATE'
userid - userid of the virtual machine
parms['vaddr'] - Virtual address
Output:
Request Handle updated with the results.
Return code - 0: ok, non-zero: error
"""
rh.printSysLog("Enter changeVM.undedicate")
parms = [
"-T", rh.userid,
"-v", rh.parms['vaddr']]
hideList = []
results = invokeSMCLI(rh,
"Image_Device_Undedicate_DM",
parms,
hideInLog=hideList)
if results['overallRC'] != 0:
# SMAPI API failed.
rh.printLn("ES", results['response'])
rh.updateResults(results) # Use results from invokeSMCLI
if results['overallRC'] == 0:
results = isLoggedOn(rh, rh.userid)
if (results['overallRC'] == 0 and results['rs'] == 0):
# Dedicate device to active configuration.
parms = [
"-T", rh.userid,
"-v", rh.parms['vaddr']]
results = invokeSMCLI(rh, "Image_Device_Undedicate", parms)
if results['overallRC'] == 0:
rh.printLn("N", "Dedicated device " + rh.parms['vaddr'] +
" to the active configuration.")
else:
# SMAPI API failed.
rh.printLn("ES", results['response'])
rh.updateResults(results) # Use results from invokeSMCLI
rh.printSysLog("Exit changeVM.undedicate, rc: " +
str(rh.results['overallRC']))
return rh.results['overallRC']
def addAEMOD(rh):
"""
Send an Activation Modification Script to the virtual machine.
Input:
Request Handle with the following properties:
function - 'CHANGEVM'
subfunction - 'AEMOD'
userid - userid of the virtual machine
parms['aeScript'] - File specification of the AE script
parms['invparms'] - invparms operand
Output:
Request Handle updated with the results.
Return code - 0: ok
Return code - 4: input error, rs - 11 AE script not found
"""
rh.printSysLog("Enter changeVM.addAEMOD")
invokeScript = "invokeScript.sh"
trunkFile = "aemod.doscript"
fileClass = "X"
tempDir = tempfile.mkdtemp()
if os.path.isfile(rh.parms['aeScript']):
# Get the short name of our activation engine modifier script
if rh.parms['aeScript'].startswith("/"):
s = rh.parms['aeScript']
tmpAEScript = s[s.rindex("/") + 1:]
else:
tmpAEScript = rh.parms['aeScript']
# Copy the mod script to our temp directory
shutil.copyfile(rh.parms['aeScript'], tempDir + "/" + tmpAEScript)
# Create the invocation script.
conf = "#!/bin/bash \n"
baseName = os.path.basename(rh.parms['aeScript'])
parm = "/bin/bash %s %s \n" % (baseName, rh.parms['invParms'])
fh = open(tempDir + "/" + invokeScript, "w")
fh.write(conf)
fh.write(parm)
fh.close()
# Generate the tar package for punch
tar = tarfile.open(tempDir + "/" + trunkFile, "w")
for file in os.listdir(tempDir):
tar.add(tempDir + "/" + file, arcname=file)
tar.close()
# Punch file to reader
punch2reader(rh, rh.userid, tempDir + "/" + trunkFile, fileClass)
shutil.rmtree(tempDir)
else:
# Worker script does not exist.
shutil.rmtree(tempDir)
msg = msgs.msg['0400'][1] % (modId, rh.parms['aeScript'])
rh.printLn("ES", msg)
rh.updateResults(msgs.msg['0400'][0])
rh.printSysLog("Exit changeVM.addAEMOD, rc: " +
str(rh.results['overallRC']))
return rh.results['overallRC']
def addIPL(rh):
"""
Sets the IPL statement in the virtual machine's directory entry.
Input:
Request Handle with the following properties:
function - 'CHANGEVM'
subfunction - 'IPL'
userid - userid of the virtual machine
parms['addrOrNSS'] - Address or NSS name
parms['loadparms'] - Loadparms operand (optional)
parms['parms'] - Parms operand (optional)
Output:
Request Handle updated with the results.
Return code - 0: ok, non-zero: error
"""
rh.printSysLog("Enter changeVM.addIPL")
parms = ["-T", rh.userid, "-s", rh.parms['addrOrNSS']]
if 'loadparms' in rh.parms:
parms.extend(["-l", rh.parms['loadparms']])
if 'parms' in rh.parms:
parms.extend(["-p", rh.parms['parms']])
results = invokeSMCLI(rh, "Image_IPL_Set_DM", parms)
if results['overallRC'] != 0:
# SMAPI API failed.
rh.printLn("ES", results['response'])
rh.updateResults(results) # Use results from invokeSMCLI
rh.printSysLog("Exit changeVM.addIPL, rc: " +
str(rh.results['overallRC']))
return rh.results['overallRC']
def addLOADDEV(rh):
"""
Sets the LOADDEV statement in the virtual machine's directory entry.
Input:
Request Handle with the following properties:
function - 'CHANGEVM'
subfunction - 'ADDLOADDEV'
userid - userid of the virtual machine
parms['boot'] - Boot program number
parms['addr'] - Logical block address of the boot record
parms['lun'] - One to eight-byte logical unit number
of the FCP-I/O device.
parms['wwpn'] - World-Wide Port Number
parms['scpDataType'] - SCP data type
parms['scpData'] - Designates information to be passed to the
program is loaded during guest IPL.
Note that any of the parms may be left blank, in which case
we will not update them.
Output:
Request Handle updated with the results.
Return code - 0: ok, non-zero: error
"""
rh.printSysLog("Enter changeVM.addLOADDEV")
# scpDataType and scpData must appear or disappear concurrently
if ('scpData' in rh.parms and 'scpDataType' not in rh.parms):
msg = msgs.msg['0014'][1] % (modId, "scpData", "scpDataType")
rh.printLn("ES", msg)
rh.updateResults(msgs.msg['0014'][0])
return
if ('scpDataType' in rh.parms and 'scpData' not in rh.parms):
if rh.parms['scpDataType'].lower() == "delete":
scpDataType = 1
else:
# scpDataType and scpData must appear or disappear
# concurrently unless we're deleting data
msg = msgs.msg['0014'][1] % (modId, "scpDataType", "scpData")
rh.printLn("ES", msg)
rh.updateResults(msgs.msg['0014'][0])
return
scpData = ""
if 'scpDataType' in rh.parms:
if rh.parms['scpDataType'].lower() == "hex":
scpData = rh.parms['scpData']
scpDataType = 3
elif rh.parms['scpDataType'].lower() == "ebcdic":
scpData = rh.parms['scpData']
scpDataType = 2
# scpDataType not hex, ebcdic or delete
elif rh.parms['scpDataType'].lower() != "delete":
msg = msgs.msg['0016'][1] % (modId, rh.parms['scpDataType'])
rh.printLn("ES", msg)
rh.updateResults(msgs.msg['0016'][0])
return
else:
# Not specified, 0 for do nothing
scpDataType = 0
scpData = ""
if 'boot' not in rh.parms:
boot = ""
else:
boot = rh.parms['boot']
if 'addr' not in rh.parms:
block = ""
else:
block = rh.parms['addr']
if 'lun' not in rh.parms:
lun = ""
else:
lun = rh.parms['lun']
# Make sure it doesn't have the 0x prefix
lun.replace("0x", "")
if 'wwpn' not in rh.parms:
wwpn = ""
else:
wwpn = rh.parms['wwpn']
# Make sure it doesn't have the 0x prefix
wwpn.replace("0x", "")
parms = [
"-T", rh.userid,
"-b", boot,
"-k", block,
"-l", lun,
"-p", wwpn,
"-s", str(scpDataType)]
if scpData != "":
parms.extend(["-d", scpData])
results = invokeSMCLI(rh, "Image_SCSI_Characteristics_Define_DM", parms)
# SMAPI API failed.
if results['overallRC'] != 0:
rh.printLn("ES", results['response'])
rh.updateResults(results)
rh.printSysLog("Exit changeVM.addLOADDEV, rc: " +
str(rh.results['overallRC']))
return rh.results['overallRC']
def doIt(rh):
"""
Perform the requested function by invoking the subfunction handler.
Input:
Request Handle
Output:
Request Handle updated with parsed input.
Return code - 0: ok, non-zero: error
"""
rh.printSysLog("Enter changeVM.doIt")
# Show the invocation parameters, if requested.
if 'showParms' in rh.parms and rh.parms['showParms'] is True:
rh.printLn("N", "Invocation parameters: ")
rh.printLn("N", " Routine: changeVM." +
str(subfuncHandler[rh.subfunction][0]) + "(reqHandle)")
rh.printLn("N", " function: " + rh.function)
rh.printLn("N", " userid: " + rh.userid)
rh.printLn("N", " subfunction: " + rh.subfunction)
rh.printLn("N", " parms{}: ")
for key in rh.parms:
if key != 'showParms':
rh.printLn("N", " " + key + ": " +
str(rh.parms[key]))
rh.printLn("N", " ")
# Call the subfunction handler
subfuncHandler[rh.subfunction][1](rh)
rh.printSysLog("Exit changeVM.doIt, rc: " +
str(rh.results['overallRC']))
return rh.results['overallRC']
def getVersion(rh):
"""
Get the version of this function.
Input:
Request Handle
Output:
Request Handle updated with the results.
Return code - 0: ok, non-zero: error
"""
rh.printLn("N", "Version: " + version)
return 0
def help(rh):
"""
Produce help output specifically for ChangeVM functions.
Input:
Request Handle
Output:
Request Handle updated with the results.
Return code - 0: ok, non-zero: error
"""
showInvLines(rh)
showOperandLines(rh)
return 0
def parseCmdline(rh):
"""
Parse the request command input.
Input:
Request Handle
Output:
Request Handle updated with parsed input.
Return code - 0: ok, non-zero: error
"""
rh.printSysLog("Enter changeVM.parseCmdline")
if rh.totalParms >= 2:
rh.userid = rh.request[1].upper()
else:
# Userid is missing.
msg = msgs.msg['0010'][1] % modId
rh.printLn("ES", msg)
rh.updateResults(msgs.msg['0010'][0])
rh.printSysLog("Exit changeVM.parseCmdLine, rc: " +
str(rh.results['overallRC']))
return rh.results['overallRC']
if rh.totalParms == 2:
rh.subfunction = rh.userid
rh.userid = ''
if rh.totalParms >= 3:
rh.subfunction = rh.request[2].upper()
# Verify the subfunction is valid.
if rh.subfunction not in subfuncHandler:
# Subfunction is missing.
subList = ', '.join(sorted(subfuncHandler.keys()))
msg = msgs.msg['0011'][1] % (modId, subList)
rh.printLn("ES", msg)
rh.updateResults(msgs.msg['0011'][0])
# Parse the rest of the command line.
if rh.results['overallRC'] == 0:
rh.argPos = 3 # Begin Parsing at 4th operand
generalUtils.parseCmdline(rh, posOpsList, keyOpsList)
if rh.results['overallRC'] == 0:
if rh.subfunction in ['ADD3390', 'ADD9336']:
if ('fileSystem' in rh.parms and rh.parms['fileSystem'] not in
['ext2', 'ext3', 'ext4', 'xfs', 'swap']):
# Invalid file system specified.
msg = msgs.msg['0015'][1] % (modId, rh.parms['fileSystem'])
rh.printLn("ES", msg)
rh.updateResults(msgs.msg['0015'][0])
rh.printSysLog("Exit changeVM.parseCmdLine, rc: " +
str(rh.results['overallRC']))
return rh.results['overallRC']
def punchFile(rh):
"""
Punch a file to a virtual reader of the specified virtual machine.
Input:
Request Handle with the following properties:
function - 'CHANGEVM'
subfunction - 'PUNCHFILE'
userid - userid of the virtual machine
parms['class'] - Spool class (optional)
parms['file'] - Filespec of the file to punch.
Output:
Request Handle updated with the results.
Return code - 0: ok, non-zero: error
"""
rh.printSysLog("Enter changeVM.punchFile")
# Default spool class in "A" , if specified change to specified class
spoolClass = "A"
if 'class' in rh.parms:
spoolClass = str(rh.parms['class'])
punch2reader(rh, rh.userid, rh.parms['file'], spoolClass)
rh.printSysLog("Exit changeVM.punchFile, rc: " +
str(rh.results['overallRC']))
return rh.results['overallRC']
def purgeRDR(rh):
"""
Purge the reader belonging to the virtual machine.
Input:
Request Handle with the following properties:
function - 'CHANGEVM'
subfunction - 'PURGERDR'
userid - userid of the virtual machine
Output:
Request Handle updated with the results.
Return code - 0: ok, non-zero: error
"""
rh.printSysLog("Enter changeVM.purgeRDR")
results = purgeReader(rh)
rh.updateResults(results)
rh.printSysLog("Exit changeVM.purgeRDR, rc: " +
str(rh.results['overallRC']))
return rh.results['overallRC']
def removeDisk(rh):
"""
Remove a disk from a virtual machine.
Input:
Request Handle with the following properties:
function - 'CHANGEVM'
subfunction - 'REMOVEDISK'
userid - userid of the virtual machine
parms['vaddr'] - Virtual address
Output:
Request Handle updated with the results.
Return code - 0: ok, non-zero: error
"""
rh.printSysLog("Enter changeVM.removeDisk")
results = {'overallRC': 0, 'rc': 0, 'rs': 0}
# Is image logged on
loggedOn = False
results = isLoggedOn(rh, rh.userid)
if results['overallRC'] == 0:
if results['rs'] == 0:
loggedOn = True
results = disableEnableDisk(
rh,
rh.userid,
rh.parms['vaddr'],
'-d')
if results['overallRC'] != 0:
rh.printLn("ES", results['response'])
rh.updateResults(results)
if results['overallRC'] == 0 and loggedOn:
strCmd = "/sbin/vmcp detach " + rh.parms['vaddr']
results = execCmdThruIUCV(rh, rh.userid, strCmd)
if results['overallRC'] != 0:
if re.search('(^HCP\w\w\w040E)', results['response']):
# Device does not exist, ignore the error
results = {'overallRC': 0, 'rc': 0, 'rs': 0, 'response': ''}
else:
rh.printLn("ES", results['response'])
rh.updateResults(results)
if results['overallRC'] == 0:
# Remove the disk from the user entry.
parms = [
"-T", rh.userid,
"-v", rh.parms['vaddr'],
"-e", "0"]
results = invokeSMCLI(rh, "Image_Disk_Delete_DM", parms)
if results['overallRC'] != 0:
if (results['overallRC'] == 8 and results['rc'] == 208 and
results['rs'] == 36):
# Disk does not exist, ignore the error
results = {'overallRC': 0, 'rc': 0, 'rs': 0, 'response': ''}
else:
# SMAPI API failed.
rh.printLn("ES", results['response'])
rh.updateResults(results) # Use results from invokeSMCLI
else:
# Unexpected error. Message already sent.
rh.updateResults(results)
rh.printSysLog("Exit changeVM.removeDisk, rc: " +
str(rh.results['overallRC']))
return rh.results['overallRC']
def removeIPL(rh):
"""
Sets the IPL statement in the virtual machine's directory entry.
Input:
Request Handle with the following properties:
function - 'CHANGEVM'
subfunction - 'REMOVEIPL'
userid - userid of the virtual machine
Output:
Request Handle updated with the results.
Return code - 0: ok, non-zero: error
"""
rh.printSysLog("Enter changeVM.removeIPL")
parms = ["-T", rh.userid]
results = invokeSMCLI(rh, "Image_IPL_Delete_DM", parms)
if results['overallRC'] != 0:
# SMAPI API failed.
rh.printLn("ES", results['response'])
rh.updateResults(results) # Use results from invokeSMCLI
rh.printSysLog("Exit changeVM.removeIPL, rc: " +
str(rh.results['overallRC']))
return rh.results['overallRC']
def showInvLines(rh):
"""
Produce help output related to command synopsis
Input:
Request Handle
"""
if rh.subfunction != '':
rh.printLn("N", "Usage:")
rh.printLn("N", " python " + rh.cmdName +
" ChangeVM <userid> add3390 <diskPool> <vAddr>")
rh.printLn("N", " <diskSize3390> --mode " +
"<mode> --readpw <read_pw>")
rh.printLn("N", " --writepw <write_pw> " +
"--multipw <multi_pw> --filesystem <fsType>")
rh.printLn("N", " python " + rh.cmdName +
" ChangeVM <userid> add9336 <diskPool> <vAddr>")
rh.printLn("N", " <diskSize9336> --mode " +
"<mode> --readpw <read_pw>")
rh.printLn("N", " --writepw <write_pw> " +
"--multipw <multi_pw> --filesystem <fsType>")
rh.printLn("N", " python " + rh.cmdName +
" ChangeVM <userid> aemod <aeScript> --invparms <invParms>")
rh.printLn("N", " python " + rh.cmdName +
" ChangeVM <userid> IPL <addrOrNSS> --loadparms <loadParms>")
rh.printLn("N", " --parms <parmString>")
rh.printLn("N", " python " + rh.cmdName +
" ChangeVM <userid> loaddev --boot <boot> --addr <addr>")
rh.printLn("N", " --wwpn <wwpn> --lun <lun> " +
"--scpdatatype <scpDatatype> --scpdata <scp_data>")
rh.printLn("N", " python " + rh.cmdName +
" ChangeVM <userid> punchFile <file> --class <class>")
rh.printLn("N", " python " + rh.cmdName +
" ChangeVM <userid> purgeRDR")
rh.printLn("N", " python " + rh.cmdName +
" ChangeVM <userid> removedisk <vAddr>")
rh.printLn("N", " python " + rh.cmdName +
" ChangeVM <userid> removeIPL <vAddr>")
rh.printLn("N", " python " + rh.cmdName + " ChangeVM help")
rh.printLn("N", " python " + rh.cmdName +
" ChangeVM version")
return
def showOperandLines(rh):
"""
Produce help output related to operands.
Input:
Request Handle
"""
if rh.function == 'HELP':
rh.printLn("N", " For the ChangeVM function:")
else:
rh.printLn("N", "Sub-Functions(s):")
rh.printLn("N", " add3390 - Add a 3390 (ECKD) disk " +
"to a virtual machine's directory")
rh.printLn("N", " entry.")
rh.printLn("N", " add9336 - Add a 9336 (FBA) disk " +
"to virtual machine's directory")
rh.printLn("N", " entry.")
rh.printLn("N", " aemod - Sends an activation " +
"engine script to the managed virtual")
rh.printLn("N", " machine.")
rh.printLn("N", " help - Displays this help " +
"information.")
rh.printLn("N", " ipl - Sets the IPL statement in " +
"the virtual machine's")
rh.printLn("N", " directory entry.")
rh.printLn("N", " loaddev - Sets the LOADDEV statement " +
"in the virtual machine's")
rh.printLn("N", " directory entry.")
rh.printLn("N", " punchfile - Punch a file to a virtual " +
"reader of the specified")
rh.printLn("N", " virtual machine.")
rh.printLn("N", " purgerdr - Purges the reader " +
"belonging to the virtual machine.")
rh.printLn("N", " removedisk - " +
"Remove an mdisk from a virtual machine.")
rh.printLn("N", " removeIPL - " +
"Remove an IPL from a virtual machine's directory entry.")
rh.printLn("N", " version - " +
"show the version of the power function")
if rh.subfunction != '':
rh.printLn("N", "Operand(s):")
rh.printLn("N", " -addr <addr> - " +
"Specifies the logical block address of the")
rh.printLn("N", " " +
"boot record.")
rh.printLn("N", " <addrOrNSS> - " +
"Specifies the virtual address or NSS name")
rh.printLn("N", " to IPL.")
rh.printLn("N", " <aeScript> - " +
"aeScript is the fully qualified file")
rh.printLn("N", " " +
"specification of the script to be sent")
rh.printLn("N", " --boot <boot> - " +
"Boot program number")
rh.printLn("N", " --class <class> - " +
"The class is optional and specifies the spool")
rh.printLn("N", " " +
"class for the reader file.")
rh.printLn("N", " <diskPool> - " +
"Specifies the directory manager disk pool to")
rh.printLn("N", " " +
"use to obtain the disk.")
rh.printLn("N", " <diskSize3390> - " +
"Specifies the size of the ECKD minidisk. ")
rh.printLn("N", " <diskSize9336> - " +
"Specifies the size of the FBA type minidisk.")
rh.printLn("N", " <file> - " +
"File to punch to the target system.")
rh.printLn("N", " --filesystem <fsType> - " +
"Specifies type of filesystem to be created on")
rh.printLn("N", " the minidisk.")
rh.printLn("N", " --invparms <invParms> - " +
"Specifies the parameters to be specified in the")
rh.printLn("N", " " +
"invocation script to call the aeScript.")
rh.printLn("N", " --loadparms <loadParms> - " +
"Specifies a 1 to 8-character load parameter that")
rh.printLn("N", " " +
"is used by the IPL'd system.")
rh.printLn("N", " --lun <lun> - " +
"One to eight-byte logical unit number of the")
rh.printLn("N", " FCP-I/O device.")
rh.printLn("N", " --mode <mode> - " +
"Specifies the access mode for the minidisk.")
rh.printLn("N", " --multipw <multi_pw> - " +
"Specifies the password that allows sharing the")
rh.printLn("N", " " +
"minidisk in multiple-write mode.")
rh.printLn("N", " --parms <parmString> - " +
"Specifies a parameter string to pass to the")
rh.printLn("N", " " +
"virtual machine in general-purpose registers at")
rh.printLn("N", " " +
"user's the completion of the IPL.")
rh.printLn("N", " --readpw <read_pw> - " +
"Specifies the password that allows sharing the")
rh.printLn("N", " " +
"minidisk in read mode.")
rh.printLn("N", " --scpdata <scpdata> - " +
"Provides the SCP data information.")
rh.printLn("N", " --scpdatatype <scpdatatype> - " +
"Specifies whether the scp data is in hex,")
rh.printLn("N", " " +
"EBCDIC, or should be deleted.")
rh.printLn("N", " <userid> - " +
"Userid of the target virtual machine.")
rh.printLn("N", " <vAddr> - " +
"Virtual address of the device.")
rh.printLn("N", " --writepw <write_pw> - " +
"Specifies is the password that allows sharing")
rh.printLn("N", " " +
"the minidisk in write mode.")
rh.printLn("N", " --wwpn <wwpn> - " +
"The world-wide port number.")
return