#!/usr/bin/perl
# IBM_PROLOG_BEGIN_TAG 
# This is an automatically generated prolog. 
#  
# bos720 src/bos/usr/lib/nim/methods/c_unloadiso.pl 1.6 
#  
# Licensed Materials - Property of IBM 
#  
# COPYRIGHT International Business Machines Corp. 2008 
# All Rights Reserved 
#  
# US Government Users Restricted Rights - Use, duplication or 
# disclosure restricted by GSA ADP Schedule Contract with IBM Corp. 
#  
# IBM_PROLOG_END_TAG 
# @(#)49        1.6  src/bos/usr/lib/nim/methods/c_unloadiso.pl, cmdnim, bos720 11/25/08 07:52:04

use strict;
use warnings;
use Getopt::Long;
use Carp;
use IPC::Open3;
use IO::Select;
use File::Path;     # Used for mkpath rmtree
use File::Basename; # Used for basename

use lib '/usr/lpp/bos.sysmgt/nim/perl';
use NIMUtils;
use NIMUtils ':rc_csts'; # KO_CODE OK_CODE

# The following line is dynamically replaced at compiled time
# with the list of all IDs needed to display i18n messages.
# See the Makefile for more details.
# === START
use constant {
   ERR_OVF_REFERS	=> [1,449],
   ERR_OVF_RUNCMD	=> [1,450],
   ERR_OVF_BAD_OPTION	=> [1,451],
   ERR_OVF_MISSING_PARAM	=> [1,452],
   ERR_OVF_UNKN_OBJECT	=> [1,453],
   ERR_OVF_OPEN	=> [1,454],
   ERR_OVF_FILE_NOTFOUND	=> [1,455],
   ERR_OVF_LOCATION_NOTFOUND	=> [1,456],
   ERR_OVF_RESTORE	=> [1,457],
   ERR_OVF_UNMOUNT	=> [1,458],
   ERR_OVF_FS_EXISTS	=> [1,459],
   ERR_OVF_COLLECT_INFO	=> [1,460],
   ERR_OVF_INVALID_ENVELOPE	=> [1,461],
   ERR_OVF_DEFAULT_VALUES	=> [1,462],
   ERR_OVF_NOSPACE_FOR_REPOSITORY	=> [1,468],
   MSG_M_MKOVF_VM_SYNTAX	=> [479,492],
   MSG_M_RMOVF_VM_SYNTAX	=> [479,493],
   ATTR_OVF_VM	=> [5,820],
   H_ATTR_OVF_VM	=> [5,821],
   ATTR_OVF_ENVELOPE	=> [5,824],
   H_ATTR_OVF_ENVELOPE	=> [5,825],
   ATTR_OVF_SOURCE	=> [5,826],
   H_ATTR_OVF_SOURCE	=> [5,827],
   ATTR_OVF_ENVELOPE_UPDATE	=> [5,834],
   H_ATTR_OVF_ENVELOPE_UPDATE	=> [5,835],
   VERBOSE_ATTR_OVF_VM	=> [11,380],
   VERBOSE_ATTR_OVF_ENVELOPE	=> [11,381],
   VERBOSE_ATTR_OVF_SOURCE	=> [11,382],
   VERBOSE_ATTR_OVF_ENVELOPE_UPDATE	=> [11,384],
};
# === END

# Global variables
use vars qw($dev_name);


# return code values
use constant ERR_RC_RUNCMD	=> 1;
use constant ERR_RC_BAD_OPTION	=> 2;
use constant ERR_RC_MISSING_PARAM	=> 3;
use constant ERR_RC_UKWN_DEV	=> 4;
use constant ERR_RC_CANT_CREATE_TMPDIR	=> 5;

# List of the AIX commands used
my $LSSLOT	= "/usr/sbin/lsslot";
my $LSVOPT	= "/usr/ios/cli/ioscli lsvopt";
my $RMVOPT	= "/usr/ios/cli/ioscli rmvopt";
my $RMVDEV	= "/usr/ios/cli/ioscli rmvdev";
my $UNLOADOPT	= "/usr/ios/cli/ioscli unloadopt";

# ----------------------------------------------------------------------------
# SUBROUTINE_NAME: rmvopt
# ABSTRACT: This function does all the real work to umount the VOPT device.
# GLOBAL_MODIFIED:
# INPUT: slot_num
# INPUT: target
# OUTPUT: none
# RETURN: OK_CODE if OK
# ----------------------------------------------------------------------------
sub rmvopt()
{
	my ($rc, $cmd, $stdout, $media);
	
	#-1- Get the virtual media associated to the virtual drive
	#VTD             Media                                   Size(mb)
	#vtopt0          iso_file                                       1
	#vtopt1          No Media                                     n/a

	$cmd = "$LSVOPT";
	($rc, $stdout) = &NIMUtils::run_command($cmd, 1);
	if ($rc) {
		&NIMUtils::translate(ERR_OVF_RUNCMD, "%s: The command \"%s\" failed (rc=%s).\n", "rmvopt", $cmd, $rc);
		return (ERR_RC_RUNCMD);
	}
	if (!defined($stdout) || ($stdout eq "")) {
		# No virtual drive, nothing to do
		return (OK_CODE);
	}
	my @tmp = split(/\n/, $stdout);
	my @l = grep(/^$dev_name\s+\S+\s+\S+$/, @tmp);
	if (scalar(@l) == 0) {
		# Virtual drive not found or nothing loaded on it, nothing to do
		return (OK_CODE);
	}
	$l[0] =~ /^$dev_name\s+(\S+)\s+\S+$/;
	$media = $1;
	
	#-2- unload the virtual drive (with release option to force the unload
	#                       even if the device is always mounted by a user)
	$cmd = "$UNLOADOPT -release -vtd $dev_name";
	($rc, $stdout) = &NIMUtils::run_command($cmd, 1);
	if ($rc) {
		&NIMUtils::translate(ERR_OVF_RUNCMD, "%s: The command \"%s\" failed (rc=%s).\n", "rmvopt", $cmd, $rc);
		return (ERR_RC_RUNCMD);
	}
		
	#-5- Remove the Virtual optical device
	$cmd = "$RMVOPT -name $media";
	($rc, $stdout) = &NIMUtils::run_command($cmd, 1);
	if ($rc) {
		&NIMUtils::translate(ERR_OVF_RUNCMD, "%s: The command \"%s\" failed (rc=%s).\n", "rmvopt", $cmd, $rc);
		return (ERR_RC_RUNCMD);
	}
	
	#-4- remove the Virtual Adapter
	$cmd = "$RMVDEV -vtd $dev_name";
	($rc, $stdout) = &NIMUtils::run_command($cmd, 1);
	if ($rc) {
		&NIMUtils::translate(ERR_OVF_RUNCMD, "%s: The command \"%s\" failed (rc=%s).\n", "rmvopt", $cmd, $rc);
		return (ERR_RC_RUNCMD);
	}
	
	return OK_CODE;
}


sub dev_name_param()
{
	$dev_name = shift;
}

# ----------------------------------------------------------------------------
## BEGIN MAIN ##
# ----------------------------------------------------------------------------

# options: -a slot_num=<remote_slot_num> <vopt_iso_target_name>
# Parse the arguments
my %options;
GetOptions("a=s" => \%options,
	   "<>"  => \&dev_name_param)
  or do {
	# invalid option parameter
	&NIMUtils::translate(ERR_OVF_BAD_OPTION, "%s: Invalid option.\n", "main");
	exit(ERR_RC_BAD_OPTION);
  };

# Check that mandatory arguments are here
&NIMUtils::set_signals_handler(\&cleanup_exit);
	
if (!defined($dev_name) or ($dev_name eq ""))
{
	&NIMUtils::translate(ERR_OVF_MISSING_PARAM, "%s: A mandatory command parameter is missing on the command line.\n", "main");
	exit(ERR_RC_MISSING_PARAM);
}

# Generate and create a unique directory
my $tmpdir	= &NIMUtils::create_tmpdir("nim_tmp");
# Change the working directory to $tmpdir
chdir($tmpdir);
my ($rc) = &rmvopt();

if ($tmpdir) {
	chdir('/'); # avoid the warning on stderr
	rmtree($tmpdir);
}
exit($rc);

