void AfterEffectsBurner::slotProcessOutputLine( const QString & line, QProcess::ProcessChannel channel ) { bool com = line.contains( mCompleteRE ); bool framecom = line.contains( mFrameCompleteRE ); #ifdef Q_OS_MAC bool fatalMachError = line.contains(QRegExp("failed to name Mach port")); if( fatalMachError ) { logMessage(line); jobErrored("the Host has fatal Mach Errors until AB restarts."); mSlave->setStatus("restart"); } #endif if( framecom ) { if( taskStarted() ) { bool frameCheckFailure = false; if( !mJob.outputPath().endsWith( ".avi" ) && !mJob.outputPath().endsWith( ".mov" ) ) { QString framePath = makeFramePath( mJob.outputPath(), mFrame ); QFileInfo fi( framePath ); frameCheckFailure = !(fi.exists() && fi.isFile() && fi.size() > 0); if( !frameCheckFailure ) emit fileGenerated(framePath); QString log = QString("Frame %1 %2").arg(framePath).arg(frameCheckFailure ? "missing" : "found"); logMessage(log); } if( frameCheckFailure ) { jobErrored("AE: Got frame complete message, but frame doesn't exist or is zero bytes"); return; } logMessage("AE: Completed frame: " + QString::number(mFrame)); taskDone( mFrame ); mFrame++; if( !com && mFrame <= mFrameEnd ) taskStart( mFrame ); } } if( com ) { if( mJob.outputPath().endsWith( ".avi" ) || mJob.outputPath().endsWith( ".mov" ) ) emit fileGenerated(mJob.outputPath()); LOG_3("AEB::slotReadOutput emit'ing jobFinished()"); jobFinished(); return; } JobBurner::slotProcessOutputLine( line, channel ); }
JobBurner::JobBurner( const JobAssignment & jobAssignment, Slave * slave, int options ) : QObject( slave ) , mSlave( slave ) , mCmd( 0 ) , mJobAssignment( jobAssignment ) , mJob( jobAssignment.job() ) , mLoaded( false ) , mOutputTimer( 0 ) , mMemTimer( 0 ) , mLogFlushTimer( 0 ) , mCheckupTimer( 0 ) , mState( StateNew ) , mOptions( Options(options) ) , mCurrentCopy( 0 ) , mLogFilesReady( false ) , mLogFile( 0 ) , mLogStream( 0 ) , mCmdPid( 0 ) { mOutputTimer = new QTimer( this ); connect( mOutputTimer, SIGNAL( timeout() ), SLOT( updateOutput() ) ); mMemTimer = new QTimer( this ); connect( mMemTimer, SIGNAL( timeout() ), SLOT( checkMemory() ) ); mCheckupTimer = new QTimer( this ); connect( mCheckupTimer, SIGNAL( timeout() ), SLOT( checkup() ) ); mCheckupTimer->start(30000); /* Ensure we are actually assigned some tasks to work on */ mTaskAssignments = mJobAssignment.jobTaskAssignments(); if( mTaskAssignments.isEmpty() ) { jobErrored( QString("JobAssignment has no assigned tasks, Job Assignment key: %1").arg(mJobAssignment.key()) ); return; } // Double check that we are still assigned mJobAssignment.reload(); if( mJobAssignment.jobAssignmentStatus().status() != "ready" ) { LOG_1( "JobAssignment no longer ready, cancelling the burn" ); cancel(); return; } /* Make sure each of the tasks are still valid, some could have already been unassigned or cancelled */ /* Also verify that the jobtask record matches the assignment */ mTasks = JobTask::table()->records( mTaskAssignments.keys( JobTaskAssignment::schema()->field("fkeyjobtask")->pos() ), /*select=*/true, /*useCache=*/false ); foreach( JobTaskAssignment jta, mTaskAssignments ) { JobTask task = jta.jobTask(); if( jta.jobAssignmentStatus().status() != "ready" || task.status() != "assigned" || task.host() != Host::currentHost() ) { LOG_1( QString("JobTask no longer assigned, discarding. keyJobTask: %1 keyJobTaskAssignment: %2 jobtask status: %3 jobtaskassignment status: %4") .arg(task.key()).arg(jta.key()).arg(task.status()).arg(jta.jobAssignmentStatus().status()) ); mTaskAssignments -= jta; mTasks -= task; } }