📄 mvcrunner.py
字号:
"""
This file handles spawning encoder runs to encode a sequence of
multi-view videos. The idea is that you do
python <this-file> <args>
to run the encoder scripts. See the comments for the PrintUsage
function for details of the command line arguments and what
this script does.
"""
import glob
import sys, os, os.path, time, re, string, smtplib, socket, traceback, shutil
import JSVM_MVC_Config, CreateConfigFile, ExtractResults
from CommandTools import ImmediatePrint, DoCommand, SendMessageToUser
from naming import *
def PrintUsage():
print '\n\tUsage:\n\t%s <configFileName>.py\n' % sys.argv[0]
def Go():
"""
This is the main encoding function for the MVC python scripts.
When called, it will parse the command line and start running.
"""
if (2 != len(sys.argv)):
PrintUsage()
config = ReadMVCConfigFile( sys.argv[1] )
decodingScriptFD = MakeDecodingScriptFileDescriptor(config)
try:
i = 0
for task in MakeMVCTasks(config):
taskName = 'task_%i_as_view_%s.txt' % (i, `task.viewNumber` )
task.Run( os.path.join(task.workingDir,taskName) )
decodingScriptFD.write('# decoding for task %s\n' % taskName)
decodingScriptFD.write( task.decodingCommand + '\n' )
decodingScriptFD.flush()
i = i + 1
decodingScriptFD.write('\n#Finished decoder script at '+time.asctime())
decodingScriptFD.close()
ImmediatePrint('\n\nFinished MVC coding at time ' + time.asctime())
ImmediatePrint('Extracting results.')
ExtractResults.ExtractResultsIntoCSVFile(config.workingDir)
ImmediatePrint('Done.')
SendMessageToUser(config.adminEmail,
'Finished MVCRunner.py on ' + socket.gethostname(),
'Finished MVCRunner.py.\n\thost = %s\n\tdir = %s\n'%(
socket.gethostname(),config.workingDir))
except Exception, e:
exc_info = sys.exc_info()
msg = 'Got Exception of type %s:%s\ntraceback:\n%s' % (
`sys.exc_type`, e.__str__(), GetTracebackString(exc_info))
print msg
SendMessageToUser(config.adminEmail,
'Exception in MVCRunner.py',msg)
def ReadMVCConfigFile( configFileName ):
sys.path.insert(0,os.path.dirname(configFileName))
config = __import__(os.path.basename(configFileName).strip('.py'))
CreateConfigFile.ValidateConfig(config)
if (type('string') == type(config.switchedWorkingDir)):
config.switchedWorkingDir.strip()
if (config.switchedWorkingDir != None and
config.switchedWorkingDir != 'None' and
config.switchedWorkingDir != ''):
config.switchedWorkingDir = os.path.join(
config.switchedWorkingDir,os.path.basename(
config.workingDir.strip(os.sep)))
open(os.path.join(config.workingDir,'README.txt'),'wb').write(
'Switched to directory %s on host %s.\n' % (
config.switchedWorkingDir, socket.gethostname()))
config.workingDir = config.switchedWorkingDir
config.switchedWorkingDir = None
for directory in [os.path.dirname(os.path.dirname(config.workingDir)),
os.path.dirname(config.workingDir),
config.workingDir]:
if (not os.path.exists(directory)):
print '\nCreating directory %s\n' % `directory`
os.mkdir(directory)
MakeLocalCopiesIfNecessary(config)
return config
def MakeLocalCopiesIfNecessary( config ):
"""
If config.paramsForMVC['MakeLocalCopiesOfInputs'] is true,
then this function copies the executables and video sequences
into a subdirectory of config.workingDir and modifies config
so that things like config.paramsForMVC['BINPATH'] and
config.paramsForMVC['SOURCEPATH'] point to the local versions.
"""
if (None != config.paramsForMVC['MakeLocalCopiesOfInputs'] and
config.paramsForMVC['MakeLocalCopiesOfInputs']):
localDir = os.path.join(config.workingDir,'localData')
os.mkdir(localDir)
for origFileName in [GetEncoderExe(config),GetDecoderExe(config)]:
newFileName = os.path.join(localDir,os.path.basename(origFileName))
shutil.copyfile(origFileName,newFileName)
os.chmod(newFileName,0755)
config.paramsForMVC['BINPATH'] = localDir
localSourceDir = os.path.join(localDir,'videos')
os.mkdir(localSourceDir)
for fileName in glob.glob(os.path.join(
config.paramsForMVC['SOURCEPATH'],
config.paramsForMVC['SEQUENCE']) + '*'):
shutil.copyfile(fileName,os.path.join(localSourceDir,
os.path.basename(fileName)))
config.paramsForMVC['SOURCEPATH'] = localSourceDir
def MakeDecodingScriptFileDescriptor( config ):
decodingScriptFileName=os.path.join(config.workingDir,'decodingScript.py')
fd = open(decodingScriptFileName,'w')
fd.write('import os, sys, commands\n')
return fd
def MakeMVCTasks(config):
taskMakers = {
'SimpleHierarchicalB' : MakeTasksForSimpleHierarhicalBPrediction,
'CenteredHierarchicalB' : MakeTasksForCenteredHierarhicalBPrediction,
}
predictionStructure = config.paramsForMVC['PredictionStructure']
if ( taskMakers.has_key(predictionStructure) ):
return taskMakers[predictionStructure](config)
else:
raise 'Invalid PredictionStructure %s, must be one of\n\t%s.\n' % (
predicitonStructure, `taskMakers.keys()`)
def MakeTasksForSimpleHierarhicalBPrediction(config):
result = []
result.append( MakeIViewEncodingTask(config, 0,
ViewNumForSequence(config,0 ) ) )
numViews = len(config.paramsForMVC['SEQUENCE_NUMBERS'])
view = 1
while (view <= config.paramsForMVC['NumExtraPViews']):
result.append( MakePViewEncodingTask(
config, view, ViewNumForSequence(config,view),
ViewNumForSequence(config,view-1) ))
view = view + 1
while (view < numViews):
if (view + 1 < numViews):
result.append( MakePViewEncodingTask(
config, view+1, ViewNumForSequence(config,view+1),
ViewNumForSequence(config, view-1) ) )
result.append( MakeBViewEncodingTask(
config, view, ViewNumForSequence(config,view),
ViewNumForSequence(config, view-1),
ViewNumForSequence(config,view+1)))
view = view + 2
else:
result.append( MakePViewEncodingTask(
config, view, ViewNumForSequence(config,view),
ViewNumForSequence(config,view-1) ))
view = view + 1
return result
def MakeTasksForCenteredHierarhicalBPrediction(config):
"""
MakeTasksForCenteredHierarhicalBPrediction(config):
config: The configuration file module continaing things like
config.paramsForMVC, config.paramsForJSVM, etc.
This function creates a list of tasks for encoding a set of
sequences with the CenteredHierarchicalB mode. In this mode,
sequence 0 is coded as an I view without multiview prediciton
and all other sequences are predicted as P views from view 0.
"""
result = []
result.append( MakeIViewEncodingTask(config, 0,
ViewNumForSequence(config,0 ) ) )
numViews = len(config.paramsForMVC['SEQUENCE_NUMBERS'])
view = 1
while (view < numViews):
result.append( MakePViewEncodingTask(
config, view, ViewNumForSequence(config,view),
ViewNumForSequence(config,0) ))
view = view + 1
return result
def ViewNumForSequence(config,sequenceNumber):
"""
Use config to map the sequenceNumber to a view number.
"""
return config.paramsForMVC['SEQUENCE_NUMBERS'][sequenceNumber]
def GetEncoderExe(config):
return os.path.join(config.paramsForMVC['BINPATH'],
config.paramsForMVC['EncoderBinFile'])
def GetDecoderExe(config):
return os.path.join(config.paramsForMVC['BINPATH'],
config.paramsForMVC['DecoderBinFile'])
def MakeIViewEncodingTask(config, arbitraryIndex, viewNumber):
if ( AlreadyEncodedView(config, viewNumber) ):
return EmptyTask(config)
taskName = 'encode_sequence_%i_as_view_%i' % (
arbitraryIndex, viewNumber)
configFileName = os.path.join(config.workingDir,
'seq_%i_as_view_%i_encoder.cfg'%(
arbitraryIndex, viewNumber))
taskCommand = GetEncoderExe(config) + ' -pf ' + configFileName
configFileData = JSVM_MVC_Config.ConfigFile( config.paramsForJSVM )
configFileData.SetValue('InputFile',MakeInputFileNameForView
(config, viewNumber ))
configFileData.SetValue('OutputFile',MakeOutputFileNameForView
(config, viewNumber ))
configFileData.SetValue('ReconFile',MakeReconFileNameForView
(config, viewNumber ))
configFileData.SetValue('BasisQP',config.qp +
config.paramsForMVC['IViewDeltaQP'])
configFileData.SetValue('SequenceFormatString',
MakeSingleViewHierarchicalBFormatString(config))
configFileData.SetValue('NumRefFrames',config.paramsForMVC['SizeOfGOP'])
configFileData.SetValue('DPBSize',config.paramsForMVC['SizeOfGOP'])
configFileData.SetValue('MaxRefIdxActiveBL0',2)
configFileData.SetValue('MaxRefIdxActiveBL1',2)
configFileData.SetValue('MaxRefIdxActiveP',1)
configFileData.SetValue('VFramePeriod',0)
configFileData.SetValue('ViewLevel',0)
configFileData.SetValue('CurrentViewId',viewNumber)
configFileData.WriteConfigFile(configFileName)
decodingCommand = MakeDecodingCommand(
config, configFileData.GetValue('OutputFile'), viewNumber,[],[])
return MVCTask(taskName,taskCommand,config.workingDir,config.adminEmail,
viewNumber,decodingCommand)
def MakePViewEncodingTask(config, arbitraryIndex, viewNumber, referenceView):
if ( AlreadyEncodedView(config, viewNumber) ):
return EmptyTask(config)
taskName = 'Encode sequence %i as view %i referencing view %i' % (
arbitraryIndex, viewNumber, referenceView)
configFileName = os.path.join(config.workingDir,
'seq_%i_as_view_%i_encoder.cfg'%(
arbitraryIndex, viewNumber))
taskCommand = GetEncoderExe(config) + ' -pf ' + configFileName
configFileData = JSVM_MVC_Config.ConfigFile( config.paramsForJSVM )
configFileData.SetValue('InputFile',MakeInputFileNameForView
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -