locked
How to use WMV9 Codec with IWMSyncReader RRS feed

  • Question

  • Hi,

    I want to use the WMV9 to decode the compressed video stream.  I really want to use the WMV9 DMO by myself to decode so I am not using Windows Media Format SDK to give me the uncompressed data directly.  But the decoder doesn't work.  Please help me.

    What I am doing is as follows:

    1, use IWMSyncReader::GetNextSample in WMF SDK to output compressed video stream.  The stream is saved in INSSBuffer format.

    2, Get the output type of IWMSyncReader and set the input and output type of wmv9 codec IMediaObject accordingly.

    3, The wmv9 codec dmo needs IMediaBuffer, I simply warp INSSBuffer into a IMediaBuffer.  The interface of those two are actually the same.  For example

        STDMETHODIMP CMediaBuffer::SetLength(DWORD cbLength)
        {   
            return m_pINSSBuffer->SetLength( cbLength );
        }

    4, Use IMediaObject::ProcessInput to decode.  Now the question is that everytime the return value of IMediaObject:ProcessInput is S_FALSE...  I don't know why... Please help.

    A few other thoughts:
    1: what is the difference between INSSBuffer and IMediaBuffer interfaces?
    2: How IMediaObject::ProcessInput and IMediaObject::ProcessOutput corperates?  Who is doing actually the decoding process?
    3: For each call of IWMSyncReader::GetNextSample, what should I do with the INSSBuffer?  Should I flush it before each call?  Or will ProcessInput function manage it in some manner?

    I am totally new to WM SDK, I wish I have made myself clear.

    Thanks!
    Monday, March 9, 2009 7:07 PM

Answers

  • Hello Mike,

    I found what the problem is.  I didn't set the "DMO_INPUT_DATA_BUFFERF_SYNCPOINT" flag for the IMediaObject::ProcessInput() function.  Now working on the ProcessOutput part.  Thanks a lot.

    Xiaohan
    • Marked as answer by Mike Wasson Wednesday, March 11, 2009 3:59 PM
    Tuesday, March 10, 2009 7:26 PM

All replies

  • I really want to use the WMV9 DMO by myself to decode so I am not using Windows Media Format SDK to give me the uncompressed data directly. 

    I think you mean compressed data here.

    #3: That seems right.

    #4: IMediaObject::ProcessInput can return S_FALSE to indicate "no output yet"

    http://msdn.microsoft.com/en-us/library/dd406959(VS.85).aspx

    That means you should give the decoder more input -- ie, you should get another sample from the sync reader and call ProcessInput again.

    The decoder may need several input samples before it can generate an output sample.

    #2 (2): Not sure if I understand the question, but the codec object (IMediaObject) does the decoding. You call ProcessInput to give the codec input data and ProcessOutput to get the decoded frames.

    There is some general information here: http://msdn.microsoft.com/en-us/library/dd377471(VS.85).aspx

    #3 (2): You need to call Release() when you are done with the buffer (ie after ProcessInput). If the decoder needs to hold onto the buffer, it will call AddRef internally.  

    - Mike


    Mike Wasson (SDK Documentation)
    Monday, March 9, 2009 10:52 PM
  • Hello Mike,

    Thank you for your prompt reply.

    I kept calling IMediaObject::ProcessInput until all samples are read but none of the calls returned S_OK :-(

    Now I found I didn't use the "video codec private data" for the decoder DMO.  The WM SDK document says that the decoder should use the same "video codec private data" as the encoder.  But if I have only a wmv file or the compressed stream given by the IWMSyncReader, how can I get the "video codec private data" for the decoder to work correctly?  I am totally lost here...

    Now I understand how the buffer works, thanks a lot!

    Xiaohan
    Tuesday, March 10, 2009 3:22 PM
  • The codec private data is definitely confusing. I know you have to configure it when you use the encoder. I thought the decoder would get it from the media type that you get from the Sync Reader. (I believe the codec data is written into the ASF stream header.)

    You can check by examining the media type. Compare the size of the format block (cbFormat) against the size of the format structure. If there are a few extra bytes at the end, that will be the codec private data.

    However, if the decoder succeeded the SetInputType method, then you should be OK.

    Does ProcessOutput also return S_FALSE?



    - Mike
    Mike Wasson (SDK Documentation)
    Tuesday, March 10, 2009 3:51 PM
  • Thank you for your hint.  I checked the cbFormat of the input which is 93.  And sizeof(VIDEOINFOHEADER) is 88.  Are these 5 bytes the private data?  I am really curious about what this private data is???  Googled around and no information on this at all...

    Now I have the codec private data and IMediaObject::SetInputType returns S_OK.  I assume this part should be ok.  Then why it doesn't work...

    Because IMediaObject::ProcessInput is keeping returning S_FALSE, I didn't even tried IMediaObject::ProcessOutput.  I also didn't attach an output buffer for the decoder.  Will that be a problem?  I thought about that but from what I learned from MSDN it should not be the problem.

    Thanks again for your help.

    Xiaohan

    Tuesday, March 10, 2009 4:09 PM
  • I tried to call IMdeiaObject::ProcessOutput even if he return value of IMediaObjectt::ProcessInput is S_FALSE, and the return value is E_UNEXPECTED...

    Xiaohan
    Tuesday, March 10, 2009 5:06 PM
  • Hello Mike,

    I found what the problem is.  I didn't set the "DMO_INPUT_DATA_BUFFERF_SYNCPOINT" flag for the IMediaObject::ProcessInput() function.  Now working on the ProcessOutput part.  Thanks a lot.

    Xiaohan
    • Marked as answer by Mike Wasson Wednesday, March 11, 2009 3:59 PM
    Tuesday, March 10, 2009 7:26 PM
  • Glad you got it working!

    - Mike
    Mike Wasson (SDK Documentation)
    Wednesday, March 11, 2009 3:59 PM