AAC Decoder mit Android Media Codec (Audio Stream von Gstreamer)

  • Antworten:0
Jonas Ney
  • Forum-Beiträge: 2

04.05.2016, 22:03:05 via Website

Hey!

Ich würde gerne Audio von meinem Raspberry mit Hilfe von Gstreamer an mein Android Handy senden.
In Gstreamer benutze ich folgende Pipeline:
gst-launch-1.0 audiotestsrc ! faac ! "audio/mpeg, mpegversion=4" ! mux. mpegtsmux name=mux ! udpsink host=224.0.0.1 port=8001

Dadurch erhalte ich AAC LC Audio Stream mit MPEG-TS als Container.

Ich versuche die Android App mit Android Studio selbst zu entwickeln. Die Daten empfange ich mit einem MulticastSocket. Nun muss der Audio Stream mit Media Extractor und Media Codec decodiert werden. Da Media Extractor nicht direkt auf den Socket zugreifen kann speichere ich ein Teil der Daten in eine Datei und setze diese als DataSource für den Media Extractor.

Der Media Extractor scheint teilweise zu funktionieren, er erkennt dass es sich um AAC Audio handelt. Allerdings erhalte ich viele Fehlermeldungen und es wird nichts abgespielt.
Der relevante Teil meines Codes sieht folgendermaßen aus:

MediaExtractor extractor = new MediaExtractor();
Uri path = Uri.fromFile(file);

extractor.setDataSource(path.toString());

    format = extractor.getTrackFormat(0); 
    String mime = format.getString(MediaFormat.KEY_MIME); 
    decoder = MediaCodec.createDecoderByType(mime); 
    decoder.configure(format, null, null, 0); 


    while (!stopTrack) { 


        multicastSocket.receive(packet); 

        decoder.start(); 
        data = packet.getData(); 

        inputBuffers = decoder.getInputBuffers(); 
        outputBuffers = decoder.getOutputBuffers(); 
        inputBufferIndex = decoder.dequeueInputBuffer(-1); 

        if (inputBufferIndex >= 0) 
        { 
            inputBuffer = inputBuffers[inputBufferIndex]; 
            inputBuffer.clear(); 

            inputBuffer.put(data); 

            decoder.queueInputBuffer(inputBufferIndex, 0, data.length, 0, 0); 
        } 

        bufferInfo = new MediaCodec.BufferInfo(); 
        outputBufferIndex = decoder.dequeueOutputBuffer(bufferInfo, 0); 

        while (outputBufferIndex >= 0) 
        { 
            outputBuffer = outputBuffers[outputBufferIndex]; 

            outputBuffer.position(bufferInfo.offset); 
            outputBuffer.limit(bufferInfo.offset + bufferInfo.size); 

            outData = new byte[bufferInfo.size]; 
            outputBuffer.get(outData); 

            //  Log.d("AudioDecoder", outData.length + " bytes decoded"); 

           track.write(outData, 0, outData.length); 

            decoder.releaseOutputBuffer(outputBufferIndex, false); 
            outputBufferIndex = decoder.dequeueOutputBuffer(bufferInfo, 0); 

        } 

Das hier sind die Fehlermeldungen in der Logcat:

D/ExtendedUtils: Try creating ExtendedExtractor 
E/MM_OSAL: FileSource::FileSource 
E/MM_OSAL: FileSource::FileSource m_bEveryThingOK 1 
E/MM_OSAL: MM_File_Create File Name /data/mmosal_logmask.cfg , Mode 0 
E/MM_OSAL: MM_File_Create failed .Efs Error No -1 , File Name      /data/mmosal_logmask.cfg , Mode 0 
E/MM_OSAL: Open or read fail on /data/mmosal_logmask.cfg. Possible permission denied issue. Looking for /data/misc/media/mmosal_logmask.cfg 
E/MM_OSAL: MM_File_Create File Name /data/misc/media/mmosal_logmask.cfg , Mode 0  
E/MM_OSAL: MM_File_Create failed .Efs Error No -1 , File Name /data/misc/media/mmosal_logmask.cfg , Mode 0 
E/MMParserExtractor:  FileSourceWrapper::New returned NULL 
D/ExtendedUtils: default extractor is NULL, return extended extractor 
E/MM_OSAL: FileSource::FileSource 
E/MM_OSAL: FileSource::FileSource m_bEveryThingOK 1 
E/MM_OSAL: MM_File_Create File Name /data/mmosal_logmask.cfg , Mode 0  
E/MM_OSAL: MM_File_Create failed .Efs Error No -1 , File Name /data/mmosal_logmask.cfg , Mode 0 
E/MM_OSAL: Open or read fail on /data/mmosal_logmask.cfg. Possible permission denied issue. Looking for /data/misc/media/mmosal_logmask.cfg 
E/MM_OSAL: MM_File_Create File Name /data/misc/media/mmosal_logmask.cfg , Mode 0 
E/MM_OSAL: MM_File_Create failed .Efs Error No -1 , File Name /data/misc/media/mmosal_logmask.cfg , Mode 0 
E/MM_OSAL: parseTransportStreamPacket isPESPacket failed 18954 
E/MM_OSAL: parseTransportStreamPacket isPESPacket failed 18783 
E/MM_OSAL: parseTransportStreamPacket isPESPacket failed 18954 
E/MM_OSAL: parseTransportStreamPacket isPESPacket failed 18783 
I/OMXClient: Using client-side OMX mux. 
E/OMXMaster: A component of name 'OMX.qcom.audio.decoder.aac' already exists, ignoring this one. 
D/MediaCodec: MediaCodec[kWhatConfigure]: video-output-protection: 00000000, audio-output-protection: 00000000 
E/Format:: audio/mp4a-latm 
W/SoftAAC2: aacDecoder_DecodeFrame decoderErr = 0x4004 
W/SoftAAC2: AAC decoder returned error 0x4004, substituting silence 
I/SoftAAC2: Reconfiguring decoder: 0->44100 Hz, 0->0 channels 

Wie schon gesagt schreibe ich zuerst einen Teil des Streams in eine Datei, auf welche der Extractor zugreift. Diese Datei lässt sich abspielen, auch mit den Android Music Player!
Also denke ich dass der Fehler weniger beim Senden und Empfangen, als eher beim Decodieren liegt. Ich habe mir auch eine AAC Testdatei heruntergeladen, mit dieser kommt es zu den selben Fehlermeldungen.

Wie ihr wahrscheinlich am Code erkennen könnt bin ich noch nicht sehr Fortgeschritten was Programmieren angeht und somit um jede Hilfe dankbar!

Antworten