diff -r 000000000000 -r 79dd3e2336a0 mmdevicefw/mdfunittest/codecapi/omxvorbis/src/tsu_mdf_omxvorbiscodecs_record.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/mmdevicefw/mdfunittest/codecapi/omxvorbis/src/tsu_mdf_omxvorbiscodecs_record.cpp Fri Oct 08 19:40:43 2010 +0100 @@ -0,0 +1,470 @@ +// Copyright (c) 2006-2009 Nokia Corporation and/or its subsidiary(-ies). +// All rights reserved. +// This component and the accompanying materials are made available +// under the terms of "Eclipse Public License v1.0" +// which accompanies this distribution, and is available +// at the URL "http://www.eclipse.org/legal/epl-v10.html". +// +// Initial Contributors: +// Nokia Corporation - initial contribution. +// +// Contributors: +// +// Description: +// + +/** + @file + @internalComponent +*/ + +#include "tsu_mdf_omxvorbiscodecs_record.h" +#include +#include +#include + +// for the bitrate custom interface +#include + +// +// RTestStepOmxVorbisCodecRecord +// record a Vorbis file + +/** + * Constructor + */ +RTestStepOmxVorbisCodecRecord::RTestStepOmxVorbisCodecRecord() + { + iTestStepName = _L("MM-MDF-OMXVORBISCODECS-U-0002-HP"); + iHeapSize = KTestHeapSize; + } + +/** + * So that CRecordAudioFile can set the test verdict and output messages + */ +void RTestStepOmxVorbisCodecRecord::SetVerdict(TPtrC16 aText, TVerdict aVerdict) + { + iVerdict = aVerdict; + INFO_PRINTF2(_L("---> %s"), aText.Ptr()); + } + +/** + * Do the test step + */ +TVerdict RTestStepOmxVorbisCodecRecord::DoTestStepL() + { + iRecordAudioFile = CRecordAudioFile::NewL(this); + iRecordAudioFile->StartL(); + delete iRecordAudioFile; + return iVerdict; + } + +// instructs the Hw Device Adapter to record a file +CRecordAudioFile::CRecordAudioFile(RTestStepOmxVorbisCodecs* aParent) : + CActive(EPriorityNormal), + iState(EHwDeviceCreateAndInit), + iParent(aParent) + { + } + +// +// CRecordAudioFile +// Active recorder for RTestStepOmxVorbisCodecRecord and derived test classes. + +/** + * ConstructL + */ +void CRecordAudioFile::ConstructL() + { + CActiveScheduler::Add(this); + } + +/** + * NewL + */ +CRecordAudioFile* CRecordAudioFile::NewL(RTestStepOmxVorbisCodecs* aParent) + { + CRecordAudioFile* self = new (ELeave) CRecordAudioFile(aParent); + CleanupStack::PushL(self); + self->ConstructL(); + CleanupStack::Pop(self); + return self; + } + +/** + * StartL + */ +void CRecordAudioFile::StartL() + { + SetState(EHwDeviceCreateAndInit); + CActiveScheduler::Start(); + } + +/** + * @see CActive + */ +void CRecordAudioFile::DoCancel() + { + } + +/** + * Destructor + */ +CRecordAudioFile::~CRecordAudioFile() + { + } + +/** + * SetState + */ +void CRecordAudioFile::SetState(TRecordAudioFileState aState) + { + iState = aState; + SetActive(); + TRequestStatus* status = &iStatus; + User::RequestComplete(status, KErrNone); + } + +/** + * ReadTestFileInBuffer + * reads file into buffer referenced by iSourceFile + */ +TInt CRecordAudioFile::ReadTestFileInBuffer() + { + // we don't need to strip off the wav header + + RFs fs; + fs.Connect(); + + RFile file; + TInt err = file.Open(fs, KTestEncoderPlayFile, EFileRead); + if (err == KErrNone) + { + TInt size; + err = file.Size(size); + if (err == KErrNone) + { + iSourceFile = HBufC8::NewMax(size); + if(!iSourceFile) + { + return KErrNoMemory; + } + TPtr8 ptr = iSourceFile->Des(); + file.Read(ptr,size); + file.Close(); + } + fs.Close(); + } + return err; + } + +/** + * @see MMMFHwDeviceObserver + */ +TInt CRecordAudioFile::FillThisHwBuffer(CMMFBuffer& aHwDataBuffer) + { + // RDebug::Print(_L("CRecordAudioFile::FillThisHwBuffer")); + + ReadNextBuffer(aHwDataBuffer); + return KErrNone; + } + +/** + * @see MMMFHwDeviceObserver + */ +TInt CRecordAudioFile::EmptyThisHwBuffer(CMMFBuffer& aEmptyBufferPtr) + { + // RDebug::Print(_L("CRecordAudioFile::EmptyThisHwBuffer")); + + CMMFDataBuffer* dataBuffer = static_cast(&aEmptyBufferPtr); + TInt err = KErrNone; + if(dataBuffer->Data().Size()) + { + RDebug::Print(_L("CRecordAudioFile writing buffer size %d"), dataBuffer->Data().Size()); + err = WriteDataToFile(dataBuffer->Data()); + if(err != KErrNone) + { + return err; + } + } + + err = iHwDevice->ThisHwBufferEmptied(aEmptyBufferPtr); + if(err != KErrNone) + { + return err; + } + + if(dataBuffer->LastBuffer()) + { + SetState(EHwDeviceEncodeCheckData); + iHwDevice->Stop(); + } + return err; + } + +TInt CRecordAudioFile::WriteDataToFile(TDes8& aData) + { + TInt err = KErrNone; + err = iRecordFile.Write(aData); + if(err != KErrNone) + { + return err; + } + // keep record of amount of data and the number of buffers written out + iWrittenDataTotal += aData.Size(); + iBuffersWrittenCount++; + RDebug::Print(_L("CRecordAudioFile: buffers written %d, total bytes %d"), iBuffersWrittenCount, iWrittenDataTotal); + return err; + } + +/** + * opens record file + */ +TInt CRecordAudioFile::SetUpRecordFile() + { + iFileServerSession.Connect(); + TInt err = iRecordFile.Replace(iFileServerSession, KTestEncoderRecordedFile, EFileWrite|EFileShareExclusive); + return err; + } + +/** + * closes record file + */ +void CRecordAudioFile::CloseRecordFile() + { + iRecordFile.Close(); + iFileServerSession.Close(); + } + +/** + * send chunks of data into the encoder. + */ +void CRecordAudioFile::ReadNextBuffer(CMMFBuffer& aHwDataBuffer) + { + // check if finished + if (iFinished) + { + iHwDevice->ThisHwBufferFilled(aHwDataBuffer); + SetState(EHwDeviceAllowToComplete); + return; + } + + // get a chunk of data and send it straight to the encoder + CMMFDataBuffer* dataBuffer = static_cast(&aHwDataBuffer); + + TInt srcLength = iSourceFile->Size(); + if (iSourceFileReadPos < srcLength) + { + TUint8* data_pointer = const_cast(dataBuffer->Data().Ptr()); + + TInt size = srcLength - iSourceFileReadPos; + if (size > dataBuffer->Data().MaxLength()) + { + size = dataBuffer->Data().MaxLength(); + } + Mem::Copy((TAny*)data_pointer, (TAny*)iSourceFile->Mid(iSourceFileReadPos).Ptr(), size); + + // set buffer size into the CMMFBuffer + dataBuffer->Data().SetLength(size); + iSourceFileReadPos += size; + + RDebug::Print(_L("CRecordAudioFile::data read = %d bytes"), iSourceFileReadPos); + + // callback + iHwDevice->ThisHwBufferFilled(aHwDataBuffer); + } + else + { + // no more data + RDebug::Print(_L("CRecordAudioFile::end of data")); + iFinished = ETrue; + dataBuffer->SetLastBuffer(ETrue); + iHwDevice->ThisHwBufferFilled(aHwDataBuffer); + SetState(EHwDeviceAllowToComplete); + } + } + +/** + * @see CActive + */ +void CRecordAudioFile::RunL() + { + THwDeviceInitParams initParams; + TInt err; + switch (iState) + { + case EHwDeviceCreateAndInit: + { + err = OMX_Init(); + if (err != KErrNone) + { + iParent->SetVerdict(_L("The OMX Core cannot be initialised"), EFail); + SetState(EHwDeviceError); + } + initParams.iHwDeviceObserver = this; + + // now using the AudioCodecTestAdapter + TRAP(err, iHwDevice = CMMFHwDevice::NewL(TUid::Uid(KUidHwDeviceAudioCodecTestAdapter))); + if (err != KErrNone) + { + iParent->SetVerdict(_L("The Hw Device Adapter cannot be created"), EFail); + OMX_Deinit(); + SetState(EHwDeviceError); + } + MMdfHwDeviceSetup* setup = (MMdfHwDeviceSetup*)iHwDevice->CustomInterface(KUidHwDeviceSetupInterface); + if (setup != NULL) + { + //Record is pcm16 -> pcmU8 + setup->SetDataTypesL(KMMFFourCCCodePCM16, KMMFFourCCCodeTestVorbis); + } + err = iHwDevice->Init(initParams); + if (err != KErrNone) + { + CleanupAndSetDeviceError(_L("The Hw Device Adapter cannot be initialised")); + break; + } + iParent->SetVerdict(_L("The Hw Device Adapter created & initialised")); + SetState(EHwDeviceStartEncode); + break; + } + case EHwDeviceStartEncode: + { + // if we are playing a file, first we have to open the file + err = ReadTestFileInBuffer(); + if (err == KErrNotFound) + { + CleanupAndSetDeviceError(_L("Cannot open the file to be played")); + break; + } + iParent->SetVerdict(_L("The file to be played has opened successfully")); + + err = SetUpRecordFile(); + if (err) + { + CleanupAndSetDeviceError(_L("Cannot open the file to record")); + break; + } + + // configure the HwDevice + TTaskConfig config; + config.iUid = KUidTTaskConfig; + config.iRate = KTestSampleRate; + config.iStereoMode = KTestNumChannels; + err = iHwDevice->SetConfig(config); + if (err != KErrNone) + { + CleanupAndSetDeviceError(_L("The Hw Device Adapter cannot configure")); + break; + } + + // set bitrate in the encoder - this requires a custom interface + MMMFDevSoundCustomInterfaceBitRate* bitrateCI = (MMMFDevSoundCustomInterfaceBitRate*)iHwDevice->CustomInterface(KUidCustomInterfaceDevSoundBitRate); + if (bitrateCI == NULL) + { + CleanupAndSetDeviceError(_L("The Hw Device Adapter cannot find a bitrate custom interface")); + break; + } + else + { + TRAP(err, bitrateCI->SetBitRateL(KTestBitRate)); + if (err != KErrNone) + { + CleanupAndSetDeviceError(_L("The Hw Device Adapter failed to set the bitrate")); + break; + } + } + + // tell the HwDeviceAdapter to record the file + err = iHwDevice->Start(EDevEncode, EDevOutFlow); + if (err != KErrNone) + { + CleanupAndSetDeviceError(_L("The Hw Device Adapter cannot start")); + break; + } + iParent->SetVerdict(_L("The Hw Device Adapter has started successfully")); + SetState(EHwDeviceAllowToComplete); + break; + } + case EHwDeviceEncodeCheckData: + { + iParent->SetVerdict(_L("The Hw Device Adapter has stopped successfully")); + TInt fileSize = 0; + err = iRecordFile.Size(fileSize); + if(err != KErrNone) + { + CleanupAndSetDeviceError(_L("Problem with accessing the file after writing to it")); + break; + } + + // check the recorded file against expected file size for the test to pass. + if(fileSize != KTestEncoderRecordedFileExpectedSize) + { + CleanupAndSetDeviceError(_L("Unexpected amount of data written to file")); + break; + } + // encode succeeded + SetState(EHwDeviceDone); + break; + } + case EHwDeviceAllowToComplete: + break; + case EHwDeviceDone: + { + delete iHwDevice; + OMX_Deinit(); + Cancel(); + CActiveScheduler::Stop(); + CloseRecordFile(); + break; + } + case EHwDeviceError: + { + CActiveScheduler::Stop(); + CloseRecordFile(); + break; + } + default: + { + CleanupAndSetDeviceError(_L("Unknown CRecordAudioFile iState")); + break; + } + } + } + +/** + * will close down the hardware device on error + */ +void CRecordAudioFile::CleanupAndSetDeviceError(TPtrC16 aText) + { + iParent->SetVerdict(aText, EFail); + delete iHwDevice; + OMX_Deinit(); + SetState(EHwDeviceError); + } + +/** + * @see MMMFHwDeviceObserver + */ +void CRecordAudioFile::Error(TInt aError) + { + // Completion is signified by KErrUnderflow + if (aError == KErrUnderflow && iStoppedReceived) + { + iParent->SetVerdict(_L("Success")); + } + else + { + iParent->SetVerdict(_L("Error from Hw Device"), EFail); + } + SetState(EHwDeviceDone); + } + +/** + * @see MMMFHwDeviceObserver + */ +void CRecordAudioFile::Stopped() + { + iStoppedReceived = ETrue; + } + +// end