# $Header: /netrcs/oracle/network/nm/nmi/jobs/rdbms/backup/RCS/snmijrbb.tcl,v 1.6 1996/07/14 17:00:00 jjkenned Exp $ 
# 
# copyright (c) 1996 by the Oracle Corporation 
# 
# NAME: 
# 
#  snmijrbb.tcl : Script to backup a tablespace 
# 
# ARGUMENTS: 
#         
#        Argv(0) : Connect string 
#        Argv(1) : parameters to the input script 
# 
#        Actual scripts to run are in $oramsg(orainput) 
#
#
#	11/12/1996	mbyrne
#	Changed the network target to net30 for Version 8.0.2
# 
# $Log: snmijrbb.tcl,v $ 
# Revision 1.6  1996/07/14  17:00:00  dnakos & jjkenned
# bugfix: NT port, no backup to tape
#
# Revision 1.5  1996/05/17  17:52:24  yliu 
# bugfix: backup to disk/tape/oscommand + job fails if 'copy' fails 
# requires vab & vojt Ver. 1.3 
# 
# Revision 1.5  1996/04/25  15:00:00  jjkenned 
# bugfix: backup to disk/tape/oscommand + job fails if 'copy' fails  
#  requires vab & vojt Ver. 1.3 
# 
# Revision 1.4  1996/04/25  10:00:00  jjkenned 
# bugfix: was not possible to copy multiple tablespaces 
# 
# Revision 1.3  1996/03/29  18:00:00  jjkenned/abalabri 
# bugfix to allow backup to disk to work (tape & OSCommand do not) 
# 
# Revision 1.2  1996/03/07  18:58:11  yliu 
# new version from the console group 
# 

set  prev_ts_status	"OFFLINE" 
set  backup_debug	0 
 
oradefine job /oracle/rdbms/backup/backupts description=VOC-02061 
oraarguments connect_str requireddbstate backupmode tablespaces tsdfnum datafiles destination copyproc copyargs 
 
oravardesc connect_str oracle_signon message=VOC-02062 
oravardesc requireddbstate string message=VOC-02063 
oravardesc backupmode string message=VOC-02063 
oravardesc tablespaces string message=VOC-02063 
oravardesc tsdfnum string message=VOC-02063 
oravardesc datafiles string message=VOC-02063 
oravardesc destination string message=VOC-02063 
oravardesc copyproc string message=VOC-02063 
oravardesc copyargs string message=VOC-02063 
oradefine end 
 
global oramsg 

set connect_str 	[lindex $argv 0] 
set requireddbstate 	[lindex $argv 1] 
set backupmode		[lindex $argv 2] 
set tablespaces		[lindex $argv 3] 
set tsdfnum		[lindex $argv 4] 
set datafiles		[lindex $argv 5] 
set destination		[lindex $argv 6] 
set copyproc		[lindex $argv 7] 
set copyargs		[lindex $argv 8] 


set jobid		$oramsg(jobid) 

 
proc ourfail { Cursor str } { 
   cleanup $Cursor 
 
   orafail $str 
} 
 
 
proc cleanup { Cursor } { 
   global orasmp_LogonOK  
   global lda 
 
   if { $orasmp_LogonOK == "TRUE" } { 
      oraclose $Cursor 
      oralogoff $lda 
   } 
} 
 
proc DebugPuts { str } { 
   global backup_debug 
 
   if { $backup_debug } {  
     puts $str 
   } 
} 
 
# --------------------------------------------------------------------- # 
# This procedure will be called to clean up if the                      # 
# CopyFilesToDestination fails.             				# 
# --------------------------------------------------------------------- # 
# 
proc CleanupCopyFiles { TablespaceName JobNo Cursor Online DBStarted} {  
    if { $Online == "ONLINE" } { 
	DebugPuts "Cleaning up Online backup" 
	EndHotBackupMode $TablespaceName $JobNo $Cursor 
    } else { 
	DebugPuts "Cleaning up Offline backup"  
	EndColdBackupMode $TablespaceName $DBStarted $JobNo $Cursor 
    }    
} 
                   
proc CopyFilesToDirectory { Datafiles Destination TablespaceName JobNo Cursor Online DBStarted } { 
    DebugPuts "CopyFilesToDirectory: Begin" 
 
    set files [eval glob $Datafiles]  
 
    DebugPuts "  Files = $files" 

    for { set i 0 } { $i < [llength $files] } { incr i } { 
	if {[catch { exec [dosifypath [OCOPY]] [dosifypath [lindex $files $i]] [dosifypath $Destination] } message]} {  
	    CleanupCopyFiles $TablespaceName $JobNo $Cursor $Online $DBStarted 
	    ourfail $Cursor $message 
	} 
    } 
 
    DebugPuts "CopyFilesToDirectory: End" 
} 
 
 
                       
proc CopyFilesToTape { Datafiles Destination  TablespaceName JobNo Cursor Online DBStarted } { 
#DebugPuts "CopyFilesToTape: Begin" 
# 
#    set files [eval glob $Datafiles]  
#DebugPuts "  Files = $files" 
# 
#    if {[catch { eval exec tar -cf $Destination $files } message] } { 
#        CleanupCopyFiles $TablespaceName $JobNo $Cursor $Online $DBStarted 
#	ourfail $Cursor $message 
#    } 
#DebugPuts "CopyFilesToTape: End" 
CleanupCopyFiles $TablespaceName $JobNo $Cursor $Online $DBStarted 
ourfail $Cursor [msgtxt1 [NETWORK] nms 1012]
} 
 
 
                        
proc CopyFilesUsingCommand { Datafiles Destination  TablespaceName JobNo Cursor Online DBStarted } { 
DebugPuts "CopyFilesUsingCommand: Begin" 

#	set files [glob $Datafiles]  
	set files $Datafiles
DebugPuts "  Files = $files"

	set Command [format [dosifypath $Destination] [dosifypath $files] ]  
DebugPuts "$Command"
	 
    if {[catch { exec $Command } message] } { 
	    CleanupCopyFiles $TablespaceName $JobNo $Cursor $Online $DBStarted 
	    ourfail $Cursor $message 
	} 
DebugPuts "CopyFilesUsingCommand: End" 
 
 
} 
 
 
# --------------------------------------------------------------------- # 
# This procedure will call the procedure supplied in augument CopyProc.	# 
#									# 
# --------------------------------------------------------------------- # 
# 
# 
proc CopyFilesToDestination { CopyProc Datafiles Destination TablespaceName JobNo Cursor Online DBStarted} { 
DebugPuts "CopyFilesToDestination: Start" 
 
#DebugPuts "CopyFilesToDestination: CopyArgs is $CopyArgs " 
DebugPuts "CopyFilesToDestination: Datafiles is $Datafiles " 
DebugPuts "CopyFilesToDestination: Destination is $Destination " 
 
eval $CopyProc [list $Datafiles] $Destination $TablespaceName $JobNo $Cursor $Online $DBStarted 

DebugPuts "CopyFilesToDestination: End" 
} 


# 
# --------------------------------------------------------------------- # 
# This procedure will be called to check if smp_offline_backup_lock exists.# 
#									# 
# --------------------------------------------------------------------- # 
# 
proc Validateoffline_backupTables { Cursor } { 
DebugPuts "Validateoffline_backupTables: Start" 
 
#  Before we do anything else, we need to check to see  
#  if an OFFLINE backup is in the prep stage for either  
#  the database or the tablespace  
 
	set sql { create table smp_offline_backup_lock(object_name varchar2(255), job# number) }
	orasql $Cursor $sql 
	set sql { create public synonym smp_offline_backup_lock for smp_offline_backup_lock }
	orasql $Cursor $sql 
	set sql { grant all on smp_offline_backup_lock to DBA}
	orasql $Cursor $sql 

DebugPuts "Validateoffline_backupTables: End" 
}

# 
# --------------------------------------------------------------------- # 
# This procedure will be called to check if smp_oltbs_jobs exists.# 
#									# 
# --------------------------------------------------------------------- # 
# 
proc Validateoltbs_jobsTables { Cursor } { 
DebugPuts "Validateoltbs_jobsTables: Start" 
 
#  Before we do anything else, we need to check to see  
#  if an OFFLINE backup is in the prep stage for either  
#  the database or the tablespace  
 
	set sql { create table smp_oltbs_jobs(object_name varchar2(255), job# number) }
	orasql $Cursor $sql 
	set sql { create public synonym smp_oltbs_jobs for smp_oltbs_jobs }
	orasql $Cursor $sql 
	set sql { grant all on smp_oltbs_jobs to DBA }
	orasql $Cursor $sql 

DebugPuts "Validateoltbs_jobsTables: End" 
}

# 
# --------------------------------------------------------------------- # 
# This procedure will be called to start the hot backup.		# 
#									# 
# --------------------------------------------------------------------- # 
# 
proc StartHotBackupMode { TablespaceName JobNo Cursor } { 
DebugPuts "StartHotBackupMode: Start" 
 
#  Before we do anything else, we need to check to see  
#  if an OFFLINE backup is in the prep stage for either  
#  the database or the tablespace  
	global oramsg 
    set tblspname [format '%s' $TablespaceName]  
    set sql { SELECT COUNT(*) FROM smp_offline_backup_lock WHERE ( OBJECT_NAME = 'DATABASE' OR OBJECT_NAME = } 
    set sql [concat $sql $tblspname )]  
	set code [catch { orasql $Cursor $sql }]
    if {$code != 0} { 
		if {$oramsg(rc) == 942} {
		Validateoffline_backupTables $Cursor 
		set tblspname [format '%s' $TablespaceName]  
		set sql { SELECT COUNT(*) FROM smp_offline_backup_lock WHERE ( OBJECT_NAME = 'DATABASE' OR OBJECT_NAME = } 
		set sql [concat $sql $tblspname )]  
		if {[catch { orasql $Cursor $sql }] } { 
		DebugPuts "Call to SELECT COUNT(*) FROM smp_offline_backup_lock failed" 
		ourfail $Cursor [msgtxt [NETWORK] nms 5001] 
	}  
	} else {
		DebugPuts "Call to SELECT COUNT(*) FROM smp_offline_backup_lock failed" 
		ourfail $Cursor [msgtxt [NETWORK] nms 5001]
    }
    } 
 
    set count [orafetch $Cursor] 
    if { $count > 0 } {  
#  An offline backup is in progress - abort  
 
	ourfail $Cursor [msgtxt [NETWORK] nms  5002] 
    }  
  
#  We need to check the status of the tablespace  
    set sql { SELECT STATUS from sys.dba_tablespaces WHERE TABLESPACE_NAME = } 
    set sql [concat $sql $tblspname] 
  
    if {[catch { orasql $Cursor $sql }] } { 
	DebugPuts "Call to SELECT STATUS from sys.dba_tablespaces failed" 
	ourfail $Cursor [msgtxt [NETWORK] nms  5001] 
    } 
 
    set status [orafetch $Cursor] 
    if { $status == "OFFLINE" } {  
 
#  The tablespace is offline, we need it online,  
#  we could place it online or abort - we'll abort  
	ourfail $Cursor [msgtxt [NETWORK] nms  5003] 
 
#  The status could either be ONLINE or ACTIVE  
    } elseif { $status == "ONLINE" } {  
 
    set tblspname [format '%s' $TablespaceName] 
    set sql { SELECT COUNT(*) FROM smp_oltbs_jobs WHERE ( OBJECT_NAME = } 
    set sql [concat $sql $tblspname )]
    if {[catch { orasql $Cursor $sql }] } { 
		if {$oramsg(rc) == 942} {
	Validateoltbs_jobsTables $Cursor 
    set tblspname [format '%s' $TablespaceName] 
    set sql { SELECT COUNT(*) FROM smp_oltbs_jobs WHERE ( OBJECT_NAME = } 
    set sql [concat $sql $tblspname )]
    if {[catch { orasql $Cursor $sql }]} { 
	DebugPuts "Call to SELECT COUNT (*) from smp_oltbs_jobs failed" 
	ourfail $Cursor [msgtxt [NETWORK] nms 5004] 
    } 
	} else {
		DebugPuts "Call to SELECT COUNT (*) from smp_oltbs_jobs failed" 
		ourfail $Cursor [msgtxt [NETWORK] nms 5004] 
	}
    } 
  
# if the count is nonzero, this means that someone else has already 
# set the tablespace in the backup mode. 
# otherwise, we will put it in Backup Mode. 
 
    set count [orafetch $Cursor] 
    if { $count == 0 } {  
        DebugPuts "Putting Tablespace in the Backup Mode" 
 
#  We can go ahead and start backup mode  
	set sql " ALTER TABLESPACE $TablespaceName BEGIN BACKUP " 
 
DebugPuts "SQL:  $sql" 
 
	if {[catch { orasql $Cursor $sql }] } { 
	    DebugPuts "Call to ALTER TABLESPACE BEGIN BACKUP failed" 
	    ourfail $Cursor [msgtxt [NETWORK] nms  5001] 
	}  
 
    } 
 
 
    set sql { INSERT INTO smp_oltbs_jobs VALUES ( } 
    set sql [concat $sql $tblspname, $JobNo )] 
 
    if {[catch { orasql $Cursor $sql }] } { 
        DebugPuts "Call to INSERT INTO smp_oltbs_jobs failed" 
        ourfail $Cursor [msgtxt [NETWORK] nms 5001] 
    } 
     
    set sql { COMMIT }  
    if {[catch { orasql $Cursor $sql }] } {  
        DebugPuts "Call to COMMIT failed" 
        ourfail $Cursor [msgtxt [NETWORK] nms 5001] 
    }  
 
    }  
DebugPuts "StartHotBackupMode: End" 
}  
 
 
 
# --------------------------------------------------------------------- # 
# This procedure will be called to terminate the hot backup.            # 
#									# 
# --------------------------------------------------------------------- # 
# 
proc EndHotBackupMode { TablespaceName JobNo Cursor } {  
 
#  Remove the entry for our process.. 
	global oramsg 

    set tblspname [format '%s' $TablespaceName] 
    set sql { DELETE smp_oltbs_jobs WHERE ( OBJECT_NAME = } 
    set sql [concat $sql $tblspname AND JOB# = $JobNo )] 
     
    if {[catch { orasql $Cursor $sql }]} { 
        DebugPuts "Call to DELETE failed" 
        ourfail $Cursor [msgtxt [NETWORK] nms 5004] 
    } 
 
    set sql { COMMIT }    
    if {[catch { orasql $Cursor $sql }]} {  
        DebugPuts "Call to COMMIT failed"  
        ourfail $Cursor [msgtxt [NETWORK] nms 5004] 
    }  
 
#  Check if anyone else has registered an interest in this Tablespace: 
    set sql { SELECT COUNT(*) FROM smp_oltbs_jobs WHERE ( OBJECT_NAME = } 
    set sql [concat $sql $tblspname )] 
    if {[catch { orasql $Cursor $sql }] } {
		if {$oramsg(rc) == 942} {
	Validateoltbs_jobsTables $Cursor 
    set sql { SELECT COUNT(*) FROM smp_oltbs_jobs WHERE ( OBJECT_NAME = } 
    set sql [concat $sql $tblspname )] 
    if {[catch { orasql $Cursor $sql }]} { 
	DebugPuts "Call to SELECT COUNT (*) from smp_oltbs_jobs failed" 
	ourfail $Cursor [msgtxt [NETWORK] nms 5004] 
    } 
	} else {
		DebugPuts "Call to SELECT COUNT (*) from smp_oltbs_jobs failed" 
		ourfail $Cursor [msgtxt [NETWORK] nms 5004] 
	}
    } 
  
    set count [orafetch $Cursor] 
    if { $count == 0 } {  
 
#  We are the only job interested in the status of the  
#  tablespace. We can go ahead and end backup mode  
DebugPuts "Count in smp_oltbs_jobs is 1.  Ending Backup for Tablespace!" 
 
	set sql " ALTER TABLESPACE $TablespaceName END BACKUP "  
	if {[catch { orasql $Cursor $sql }]} { 
	    DebugPuts "Call to ALTER TABLESPACE END BACKUP failed" 
	    ourfail $Cursor [msgtxt [NETWORK] nms 5004] 
	} 
  
    } else { 
DebugPuts "Count in smp_oltbs_jobs is $count.  Skipping EndBackup for 
Tablespace!" 
    } 
 
#  Else, someone else is using the tablespace. Do nothing ! 
DebugPuts "EndHotBackupMode: End" 
}  
 
# 
# --------------------------------------------------------------------- # 
# This procedure will be called to start the cold backup.		# 
#									# 
# --------------------------------------------------------------------- # 
# 
proc StartColdBackupMode { TablespaceName DBStarted JobNo Cursor } { 
DebugPuts "StartColdBackupMode: Start" 
 
    global  prev_ts_status	 
	global oramsg

    if { $DBStarted } { 
 
#  First check to see if  an offline backup is about to happen 
	set tblspname [format '%s' $TablespaceName] 
	set sql { SELECT COUNT(*) FROM smp_offline_backup_lock WHERE ( OBJECT_NAME = 'DATABASE' OR OBJECT_NAME = } 
 
 
	set sql [concat $sql $tblspname )] 
    if {[catch { orasql $Cursor $sql }] } {
		if {$oramsg(rc) == 942} {
		Validateoffline_backupTables $Cursor 
		set tblspname [format '%s' $TablespaceName] 
		set sql { SELECT COUNT(*) FROM smp_offline_backup_lock WHERE ( OBJECT_NAME = 'DATABASE' OR OBJECT_NAME = } 
 
 
		set sql [concat $sql $tblspname )] 
		if {[catch { orasql $Cursor $sql }]} { 
			DebugPuts "Call to SELECT COUNT(*) failed" 
			ourfail $Cursor [msgtxt [NETWORK] nms 5005] 
		} 
		} else {
			DebugPuts "Call to SELECT COUNT(*) failed" 
			ourfail $Cursor [msgtxt [NETWORK] nms 5005] 
	}
    } 
  
	set count [orafetch $Cursor] 
	if { $count != 0 } {  
 
#  An offline backup is about to take place  
#  no need to perform this backup as the active   
#  backup will include this tablespace  
	   ourfail $Cursor [msgtxt [NETWORK] nms 5006] 
	} else {  
 
#  There are no current backups, we need to register  
	    set sql { INSERT INTO smp_offline_backup_lock VALUES ( } 
	    set sql [concat $sql $tblspname, $JobNo )] 
 
	    if {[catch { orasql $Cursor $sql }] } { 
		DebugPuts "Call to INSERT INTO smp_offline_backup_lock failed" 
	        ourfail $Cursor [msgtxt [NETWORK] nms 5005] 
	    }  
  
	    set sql { COMMIT } 
	    if {[catch { orasql $Cursor $sql }] } {  
		DebugPuts "Call to COMMIT failed"  
		ourfail $Cursor [msgtxt [NETWORK] nms 5005] 
	    }  
  
#  Find out the current state so that we can restore it  
        set sql { SELECT STATUS FROM sys.dba_tablespaces WHERE TABLESPACE_NAME = }                   
 
        set sql [concat $sql $tblspname]           
 
        if {[catch { orasql $Cursor $sql }] } {  
            DebugPuts "Call to SELECT failed: Unlocking"  
	    CleanupOfflineBackupLock $TablespaceName $JobNo $Cursor 
	    ourfail $Cursor [msgtxt [NETWORK] nms 5007] 
	} 
 
DebugPuts "Before setting prev_ts_status in StartCold!"  
 
	set prev_ts_status [orafetch $Cursor] 
 
#  Now offline the tablespace if the previous state is ONLINE. 
	  if { $prev_ts_status == "ONLINE" } { 
	    set sql { ALTER TABLESPACE } 
	    set sql [concat $sql $TablespaceName OFFLINE NORMAL] 
 
	    if {[catch { orasql $Cursor $sql }] } { 
		DebugPuts "Call to ALTER TABLESPACE OFFLINE NORMAL failed: Unlocking" 
	        CleanupOfflineBackupLock $TablespaceName $JobNo $Cursor 
		ourfail $Cursor [msgtxt [NETWORK] nms 5005] 
	    }  
          } 
#  The Database is not started, therefore we don?t have to do anything  
	} 
    } 
DebugPuts "StartColdBackupMode: End" 
}  
 
 
# -----------------------------------------------# 
# This procedure will delete the entry off the 
# smp_offline_backup_lock table. 
# -----------------------------------------------# 
proc CleanupOfflineBackupLock { TablespaceName JobNo Cursor } { 
 	set tblspname [format '%s' $TablespaceName] 
 
#  We need to remove the lock on the tablespace  
#  Execute the SQL statement. 
	set sql { DELETE smp_offline_backup_lock WHERE ( OBJECT_NAME = } 
	set sql [concat $sql $tblspname AND JOB# = $JobNo )] 
	if {[catch { orasql $Cursor $sql }]} { 
	    DebugPuts "Call to DELETE smp_offline_backup_lock failed" 
	    ourfail $Cursor [msgtxt [NETWORK] nms 5007] 
	} 
 
        set sql { COMMIT } 
        if {[catch { orasql $Cursor $sql }]} {  
            DebugPuts "Call to COMMIT failed"  
	    ourfail $Cursor [msgtxt [NETWORK] nms 5007] 
        }  
} 
									
							  
# --------------------------------------------------------------------- # 
# This procedure will be called to terminate the cold backup.		# 
#									# 
# --------------------------------------------------------------------- # 
# 
proc EndColdBackupMode { TablespaceName DBStarted JobNo Cursor } { 
DebugPuts "EndColdBackupMode: Start" 
 
    global  prev_ts_status	 
 
    if { $DBStarted } { 
	CleanupOfflineBackupLock $TablespaceName $JobNo $Cursor 
 
 	set tblspname [format '%s' $TablespaceName] 
 
#  We need to remove the lock on the tablespace  
#  Execute the SQL statement. 
	set sql { DELETE smp_offline_backup_lock WHERE ( OBJECT_NAME = } 
	set sql [concat $sql $tblspname AND JOB# = $JobNo )] 
	if {[catch { orasql $Cursor $sql }]} { 
	    DebugPuts "Call to DELETE smp_offline_backup_lock failed" 
	    ourfail $Cursor [msgtxt [NETWORK] nms 5007] 
	} 
 
        set sql { COMMIT } 
        if {[catch { orasql $Cursor $sql }]} {  
           DebugPuts "Call to COMMIT failed"  
	    ourfail $Cursor [msgtxt [NETWORK] nms 5007] 
        }  
 
# if previous status is ONLINE, we will bring it back to online: 
	if { $prev_ts_status == "ONLINE" } { 
 
DebugPuts "Previous state was ONLINE, therefore making it ONLINE!" 
 
#  Now ONLINE the TABLESPACE 
            set sql { ALTER TABLESPACE }  
            set sql [concat $sql $TablespaceName ONLINE]  
 
            if {[catch { orasql $Cursor $sql }] } {  
		DebugPuts "Call to ALTER TABLESPACE ONLINE failed" 
		ourfail $Cursor [msgtxt [NETWORK] nms 5007] 
	    } 
	} else { 
DebugPuts "Previous state was OFFLINE, ignoring it!" 
	} 
#  Database was not started, therefore we have no state to  
#  rollback. So Do nothing 
    }  
DebugPuts "EndColdBackupMode: End" 
}  
 
 
 
proc BackupTablespace { Cursor TablespaceName Datafiles Destination DBStarted Online JobNo CopyProc } { 

set mesg [format [msgtxt1 [NETWORK] nms 5012] $TablespaceName]
puts $mesg
DebugPuts "Online == $Online" 
 
    if { $Online == "\"ONLINE\"" } {  
# User has requested an online (hot) backup  
	StartHotBackupMode $TablespaceName $JobNo $Cursor 
	CopyFilesToDestination $CopyProc $Datafiles $Destination $TablespaceName $JobNo $Cursor $Online $DBStarted  
	EndHotBackupMode $TablespaceName $JobNo $Cursor 
    } else {  
#  User has requested offline (cold) backup  
#  The database may or may not be started at this point  
	StartColdBackupMode $TablespaceName $DBStarted $JobNo $Cursor 
	CopyFilesToDestination $CopyProc $Datafiles $Destination $TablespaceName $JobNo $Cursor $Online $DBStarted   
	EndColdBackupMode $TablespaceName $DBStarted $JobNo $Cursor 
    }
set mesg [format [msgtxt1 [NETWORK] nms 5014] $TablespaceName]
puts $mesg
 
puts "--------------------------------------------------------------" 
}  
 
# --------------------------------------------------------------------- # 
# This is the main routine which does the setup and determines the mode # 
# to be used.								# 
# --------------------------------------------------------------------- # 
# 
#
DebugPuts "Start of main script"
set mesg [format [msgtxt1 [NETWORK] nms 5017] $tablespaces]
puts $mesg
set mesg [format [msgtxt1 [NETWORK] nms 5018] $tsdfnum]
puts $mesg
set mesg [format [msgtxt1 [NETWORK] nms 5019] $datafiles]
puts $mesg
set mesg [format [msgtxt1 [NETWORK] nms 5020] $destination]
puts $mesg
set mesg [format [msgtxt1 [NETWORK] nms 5023] $jobid]
puts $mesg
  
set orasmp_LogonOK "FALSE" 
 
if {[catch {oralogon $connect_str} lda]} { 
    set orasmp_LogonOK "FALSE" 
 
     if { $requireddbstate == "UP" } { 
      DebugPuts "Logon Failed: login = $connect_str" 
      DebugPuts [msgtxt rdbms ora $oramsg(rc)] 
       orafail [msgtxt [NETWORK] nms  5009] 
     } 
} else { 
    set orasmp_LogonOK "TRUE" 
} 
 
if {($orasmp_LogonOK == "TRUE") && ($requireddbstate == "DOWN")} {  
    orafail [msgtxt [NETWORK] nms  5010] 
}  
if {($orasmp_LogonOK == "FALSE") && ($requireddbstate == "UP")} {  
    orafail [msgtxt [NETWORK] nms  5011] 
}  
  
    set backupmode [string trim $backupmode " "] 
    set orasmp_LogonOK [string trim $orasmp_LogonOK " "] 
 
#  The choices are online or offline  
    if { ($orasmp_LogonOK == "FALSE") && ( $backupmode == "ONLINE" ) } {  
 
#  The database is not started and an online backup has been requested  
#  We could either start the database or abort - we'll abort  
	orafail [msgtxt [NETWORK] nms 5008] 
    } 
 
    set cursor 0 
    if { $orasmp_LogonOK == "TRUE" } {  
       set cursor [oraopen $lda]  
    }  
 
set i -1 
set prevlimit 0 
 
foreach tablespace $tablespaces {  
 
	set i [expr $i+1]  
	set filenum  [lindex $tsdfnum $i] 
#	set tsdatafiles  [lrange $datafiles $prevlimit $filenum] 
	set tsdatafiles  [lrange $datafiles $prevlimit [expr $prevlimit+$filenum-1]] 
	set prevlimit  [expr $prevlimit+$filenum] 
 
 
	BackupTablespace $cursor $tablespace $tsdatafiles $destination $orasmp_LogonOK $backupmode $jobid $copyproc 
} 
 
# Close the cursor and log off. 
DebugPuts "Close the cursor and log off" 
cleanup $cursor 
