Media学习笔记

 

此文章作为在学习media过程中的记录,仅代表当下的理解和感悟。

1.  在main()函数中初始化 MediaPlayerService   /frameworks/av/media/mediaserver/main_mediaserver.cpp 

int main(int argc __unused, char **argv __unused)
{
    signal(SIGPIPE, SIG_IGN);

    sp<ProcessState> proc(ProcessState::self());
    sp<IServiceManager> sm(defaultServiceManager());
    ALOGI("ServiceManager: %p", sm.get());
    InitializeIcuOrDie();
    MediaPlayerService::instantiate(); //实例化 MediaPlayerService --》2
    ResourceManagerService::instantiate();
    registerExtensions();
    ProcessState::self()->startThreadPool();
    IPCThreadState::self()->joinThreadPool();
}

2. MediaPlayerService::instantiate()  方法的实现   /frameworks/av/media/libmediaplayerservice/MediaPlayerService.cpp

void MediaPlayerService::instantiate() {
    defaultServiceManager()->addService(
            String16("media.player"), new MediaPlayerService()); //创建MediaPlayerService 并添加至servicemanager ---->3
}

3. MediaPlayerService 的构造函数

MediaPlayerService::MediaPlayerService()
{
    ALOGV("MediaPlayerService created");
    mNextConnId = 1;

    MediaPlayerFactory::registerBuiltinFactories(); //初始化了MediaPlayerFactory----》4
}

4.MediaPlayerFactory 是播放器的制造工厂,看下它的registerBuiltinFactories()做了什么:

void MediaPlayerFactory::registerBuiltinFactories() {
    Mutex::Autolock lock_(&sLock);

    if (sInitComplete)
        return;

    IFactory* factory = new NuPlayerFactory(); //创建NuPlayer的工厂
    if (registerFactory_l(factory, NU_PLAYER) != OK)
        delete factory;
    factory = new TestPlayerFactory(); //创建TestPlayer的工厂 
    if (registerFactory_l(factory, TEST_PLAYER) != OK)
        delete factory;

    sInitComplete = true;
}
status_t MediaPlayerFactory::registerFactory_l(IFactory* factory,
                                               player_type type) {
    if (NULL == factory) {
        ALOGE("Failed to register MediaPlayerFactory of type %d, factory is"
              " NULL.", type);
        return BAD_VALUE;
    }

    //如果map中已经存在此类型的播放器工厂,直接返回已经存在code
    if (sFactoryMap.indexOfKey(type) >= 0) {  
        ALOGE("Failed to register MediaPlayerFactory of type %d, type is"
              " already registered.", type);
        return ALREADY_EXISTS;
    }
    //将类型和播放器工厂以键值对的方式存入sFactoryMap 中 
    if (sFactoryMap.add(type, factory) < 0) {
        ALOGE("Failed to register MediaPlayerFactory of type %d, failed to add"
              " to map.", type);
        return UNKNOWN_ERROR;
    }

    return OK;
}

总结以上,在main执行完之后,MediaPlayerService 被实例化并加入ServiceManager,播放器工厂被实例化并存储

5.接下来看一下MediaPlayerService的 接口IMediaPlayerService  位于:/frameworks/av/include/media/IMediaPlayerService.h

class IMediaPlayerService: public IInterface   //继承了 IInterface
{
public:
    DECLARE_META_INTERFACE(MediaPlayerService);

    virtual sp<IMediaRecorder> createMediaRecorder(const String16 &opPackageName) = 0; //----》6 创建录音器
    virtual sp<IMediaMetadataRetriever> createMetadataRetriever() = 0;//----》7 创建数据解析器
    virtual sp<IMediaPlayer> create(const sp<IMediaPlayerClient>& client,
            audio_session_t audioSessionId = AUDIO_SESSION_ALLOCATE) = 0;//----》8创建播放器
    virtual sp<IMediaCodecList> getCodecList() const = 0;//----》11 获取解码器列表

    // Connects to a remote display.
    // 'iface' specifies the address of the local interface on which to listen for
    // a connection from the remote display as an ip address and port number
    // of the form "x.x.x.x:y".  The media server should call back into the provided remote
    // display client when display connection, disconnection or errors occur.
    // The assumption is that at most one remote display will be connected to the
    // provided interface at a time.
    virtual sp<IRemoteDisplay> listenForRemoteDisplay(const String16 &opPackageName,
            const sp<IRemoteDisplayClient>& client, const String8& iface) = 0;

    // codecs and audio devices usage tracking for the battery app
    enum BatteryDataBits {
        // tracking audio codec
        kBatteryDataTrackAudio          = 0x1,
        // tracking video codec
        kBatteryDataTrackVideo          = 0x2,
        // codec is started, otherwise codec is paused
        kBatteryDataCodecStarted        = 0x4,
        // tracking decoder (for media player),
        // otherwise tracking encoder (for media recorder)
        kBatteryDataTrackDecoder        = 0x8,
        // start to play an audio on an audio device
        kBatteryDataAudioFlingerStart   = 0x10,
        // stop/pause the audio playback
        kBatteryDataAudioFlingerStop    = 0x20,
        // audio is rounted to speaker
        kBatteryDataSpeakerOn           = 0x40,
        // audio is rounted to devices other than speaker
        kBatteryDataOtherAudioDeviceOn  = 0x80,
    };

    virtual void addBatteryData(uint32_t params) = 0;
    virtual status_t pullBatteryData(Parcel* reply) = 0;
};

// ----------------------------------------------------------------------------

class BnMediaPlayerService: public BnInterface<IMediaPlayerService>   //内部类 BnMediaPlayerService 又继承于  BnInterface 
{
public:
    virtual status_t    onTransact( uint32_t code,
                                    const Parcel& data,
                                    Parcel* reply,
                                    uint32_t flags = 0);
};

}; // namespace android

目前对binder和C++都是一知半解,对IInterface和BnInterface暂不详述

其中,通过MediaPlayerService.h (位于 /frameworks/av/media/libmediaplayerservice/MediaPlayerService.h) 我们知道MediaPlayerService 继承了BnMediaPlayerService

也就是说MediaPlayerService 实现了 IMediaPlayerService接口所定义的方法,其中的关系还没有太搞清楚。

6.先来看一下sp<IMediaRecorder> createMediaRecorder(const String16 &opPackageName) 函数 ,在MediaPlayerService.cpp中实现

 

sp<IMediaRecorder> MediaPlayerService::createMediaRecorder(const String16 &opPackageName)
{
    pid_t pid = IPCThreadState::self()->getCallingPid();
    sp<MediaRecorderClient> recorder = new MediaRecorderClient(this, pid, opPackageName);//用于录音
    wp<MediaRecorderClient> w = recorder;
    Mutex::Autolock lock(mLock);
    mMediaRecorderClients.add(w);
    ALOGV("Create new media recorder client from pid %d", pid);
    return recorder;
}

//MediaRecorderClient 的位置在 : /frameworks/av/media/libmediaplayerservice/MediaRecorderClient.h 中定义的,继承了BnMediaRecorder

7. sp<IMediaMetadataRetriever> createMetadataRetriever() 

sp<IMediaMetadataRetriever> MediaPlayerService::createMetadataRetriever()
{
    pid_t pid = IPCThreadState::self()->getCallingPid();
    sp<MetadataRetrieverClient> retriever = new MetadataRetrieverClient(pid);
    ALOGV("Create new media retriever from pid %d", pid);
    return retriever;
}

// MetadataRetriever 用于获取多媒体文件的元信息metadata, 如 名称,专辑等,其中MetadataRetrieverClient 位于/frameworks/av/media/libmediaplayerservice/MetadataRetrieverClient.h
MetadataRetrieverClient.cpp 实现了 IMediaMetadataRetriever 的接口

8.sp<IMediaPlayer> create(const sp<IMediaPlayerClient>& client, audio_session_t audioSessionId = AUDIO_SESSION_ALLOCATE) 创建播放器的函数

sp<IMediaPlayer> MediaPlayerService::create(const sp<IMediaPlayerClient>& client,
        audio_session_t audioSessionId)
{
    pid_t pid = IPCThreadState::self()->getCallingPid();
    int32_t connId = android_atomic_inc(&mNextConnId);

    sp<Client> c = new Client(
            this, pid, connId, client, audioSessionId,
            IPCThreadState::self()->getCallingUid());  //Client是IMediaPlayer的代理----》9

    ALOGV("Create new client(%d) from pid %d, uid %d, ", connId, pid,
         IPCThreadState::self()->getCallingUid());

    wp<Client> w = c;
    {
        Mutex::Autolock lock(mLock);
        mClients.add(w);
    }
    return c;
}

9. Client的来历:是在MediaPlayerService.h中定义的内部类,继承了BnMediaPlayer ,声明了一个播放器的全部方法

   class Client : public BnMediaPlayer {  //BnMediaPlayer 在IMediaPlayer.h中定义 ----》10
        // IMediaPlayer interface
        virtual void            disconnect();
        virtual status_t        setVideoSurfaceTexture(
                                        const sp<IGraphicBufferProducer>& bufferProducer);
        virtual status_t        setBufferingSettings(const BufferingSettings& buffering) override;
        virtual status_t        getBufferingSettings(
                                        BufferingSettings* buffering /* nonnull */) override;
        virtual status_t        prepareAsync();
        virtual status_t        start();
        virtual status_t        stop();
        virtual status_t        pause();
        virtual status_t        isPlaying(bool* state);
        virtual status_t        setPlaybackSettings(const AudioPlaybackRate& rate);
        virtual status_t        getPlaybackSettings(AudioPlaybackRate* rate /* nonnull */);
        virtual status_t        setSyncSettings(const AVSyncSettings& rate, float videoFpsHint);
        virtual status_t        getSyncSettings(AVSyncSettings* rate /* nonnull */,
                                                float* videoFps /* nonnull */);
        virtual status_t        seekTo(
                int msec,
                MediaPlayerSeekMode mode = MediaPlayerSeekMode::SEEK_PREVIOUS_SYNC);
        virtual status_t        getCurrentPosition(int* msec);
        virtual status_t        getDuration(int* msec);
        virtual status_t        reset();
        virtual status_t        notifyAt(int64_t mediaTimeUs);
        virtual status_t        setAudioStreamType(audio_stream_type_t type);
        virtual status_t        setLooping(int loop);
        virtual status_t        setVolume(float leftVolume, float rightVolume);
        virtual status_t        invoke(const Parcel& request, Parcel *reply);
        virtual status_t        setMetadataFilter(const Parcel& filter);
        virtual status_t        getMetadata(bool update_only,
                                            bool apply_filter,
                                            Parcel *reply);
        virtual status_t        setAuxEffectSendLevel(float level);
        virtual status_t        attachAuxEffect(int effectId);
        virtual status_t        setParameter(int key, const Parcel &request);
        virtual status_t        getParameter(int key, Parcel *reply);
        virtual status_t        setRetransmitEndpoint(const struct sockaddr_in* endpoint);
        virtual status_t        getRetransmitEndpoint(struct sockaddr_in* endpoint);
        virtual status_t        setNextPlayer(const sp<IMediaPlayer>& player);

        virtual media::VolumeShaper::Status applyVolumeShaper(
                                        const sp<media::VolumeShaper::Configuration>& configuration,
                                        const sp<media::VolumeShaper::Operation>& operation) override;
        virtual sp<media::VolumeShaper::State> getVolumeShaperState(int id) override;

        sp<MediaPlayerBase>     createPlayer(player_type playerType);

        virtual status_t        setDataSource(
                        const sp<IMediaHTTPService> &httpService,
                        const char *url,
                        const KeyedVector<String8, String8> *headers);

        virtual status_t        setDataSource(int fd, int64_t offset, int64_t length);

        virtual status_t        setDataSource(const sp<IStreamSource> &source);
        virtual status_t        setDataSource(const sp<IDataSource> &source);


        sp<MediaPlayerBase>     setDataSource_pre(player_type playerType);
        status_t                setDataSource_post(const sp<MediaPlayerBase>& p,
                                                   status_t status);

                void            notify(int msg, int ext1, int ext2, const Parcel *obj);

                pid_t           pid() const { return mPid; }
        virtual status_t        dump(int fd, const Vector<String16>& args);

                audio_session_t getAudioSessionId() { return mAudioSessionId; }
        // Modular DRM
        virtual status_t prepareDrm(const uint8_t uuid[16], const Vector<uint8_t>& drmSessionId);
        virtual status_t releaseDrm();
        // AudioRouting
        virtual status_t setOutputDevice(audio_port_handle_t deviceId);
        virtual status_t getRoutedDeviceId(audio_port_handle_t* deviceId);
        virtual status_t enableAudioDeviceCallback(bool enabled);

    private:
        class ServiceDeathNotifier:
                public IBinder::DeathRecipient,
                public ::android::hardware::hidl_death_recipient
        {
        public:
            ServiceDeathNotifier(
                    const sp<IBinder>& service,
                    const sp<MediaPlayerBase>& listener,
                    int which);
            ServiceDeathNotifier(
                    const sp<IOmx>& omx,
                    const sp<MediaPlayerBase>& listener,
                    int which);
            virtual ~ServiceDeathNotifier();
            virtual void binderDied(const wp<IBinder>& who);
            virtual void serviceDied(
                    uint64_t cookie,
                    const wp<::android::hidl::base::V1_0::IBase>& who);
            void unlinkToDeath();

        private:
            int mWhich;
            sp<IBinder> mService;
            sp<IOmx> mOmx;
            wp<MediaPlayerBase> mListener;
        };

        class AudioDeviceUpdatedNotifier: public AudioSystem::AudioDeviceCallback
        {
        public:
            AudioDeviceUpdatedNotifier(const sp<MediaPlayerBase>& listener) {
                mListener = listener;
            }
            ~AudioDeviceUpdatedNotifier() {}

            virtual void onAudioDeviceUpdate(audio_io_handle_t audioIo,
                                             audio_port_handle_t deviceId);

        private:
            wp<MediaPlayerBase> mListener;
        };

        void clearDeathNotifiers_l();

        friend class MediaPlayerService;
                                Client( const sp<MediaPlayerService>& service,
                                        pid_t pid,
                                        int32_t connId,
                                        const sp<IMediaPlayerClient>& client,
                                        audio_session_t audioSessionId,
                                        uid_t uid);
                                Client();
        virtual                 ~Client();

                void            deletePlayer();

        sp<MediaPlayerBase>     getPlayer() const { Mutex::Autolock lock(mLock); return mPlayer; }



        // @param type Of the metadata to be tested.
        // @return true if the metadata should be dropped according to
        //              the filters.
        bool shouldDropMetadata(media::Metadata::Type type) const;

        // Add a new element to the set of metadata updated. Noop if
        // the element exists already.
        // @param type Of the metadata to be recorded.
        void addNewMetadataUpdate(media::Metadata::Type type);

        // Disconnect from the currently connected ANativeWindow.
        void disconnectNativeWindow_l();

        status_t setAudioAttributes_l(const Parcel &request);

        class Listener : public MediaPlayerBase::Listener {
        public:
            Listener(const wp<Client> &client) : mClient(client) {}
            virtual ~Listener() {}
            virtual void notify(int msg, int ext1, int ext2, const Parcel *obj) {
                sp<Client> client = mClient.promote();
                if (client != NULL) {
                    client->notify(msg, ext1, ext2, obj);
                }
            }
        private:
            wp<Client> mClient;
        };

        mutable     Mutex                         mLock;
                    sp<MediaPlayerBase>           mPlayer;
                    sp<MediaPlayerService>        mService;
                    sp<IMediaPlayerClient>        mClient;
                    sp<AudioOutput>               mAudioOutput;
                    pid_t                         mPid;
                    status_t                      mStatus;
                    bool                          mLoop;
                    int32_t                       mConnId;
                    audio_session_t               mAudioSessionId;
                    audio_attributes_t *          mAudioAttributes;
                    uid_t                         mUid;
                    sp<ANativeWindow>             mConnectedWindow;
                    sp<IBinder>                   mConnectedWindowBinder;
                    struct sockaddr_in            mRetransmitEndpoint;
                    bool                          mRetransmitEndpointValid;
                    sp<Client>                    mNextClient;
                    sp<MediaPlayerBase::Listener> mListener;

        // Metadata filters.
        media::Metadata::Filter mMetadataAllow;  // protected by mLock
        media::Metadata::Filter mMetadataDrop;  // protected by mLock

        // Metadata updated. For each MEDIA_INFO_METADATA_UPDATE
        // notification we try to update mMetadataUpdated which is a
        // set: no duplicate.
        // getMetadata clears this set.
        media::Metadata::Filter mMetadataUpdated;  // protected by mLock

        sp<ServiceDeathNotifier> mExtractorDeathListener;
        sp<ServiceDeathNotifier> mCodecDeathListener;
        sp<AudioDeviceUpdatedNotifier> mAudioDeviceUpdatedListener;
#if CALLBACK_ANTAGONIZER
                    Antagonizer*                  mAntagonizer;
#endif
    }; // Client

10.看一下IMediaPlayer.h     /frameworks/av/media/libmedia/include/media/IMediaPlayer.h   定义了播放器的所有的接口

class IMediaPlayer: public IInterface
{
public:
    DECLARE_META_INTERFACE(MediaPlayer);

    virtual void            disconnect() = 0;

    virtual status_t        setDataSource(
            const sp<IMediaHTTPService> &httpService,
            const char *url,
            const KeyedVector<String8, String8>* headers) = 0;

    virtual status_t        setDataSource(int fd, int64_t offset, int64_t length) = 0;
    virtual status_t        setDataSource(const sp<IStreamSource>& source) = 0;
    virtual status_t        setDataSource(const sp<IDataSource>& source) = 0;
    virtual status_t        setVideoSurfaceTexture(
                                    const sp<IGraphicBufferProducer>& bufferProducer) = 0;
    virtual status_t        getBufferingSettings(
                                    BufferingSettings* buffering /* nonnull */) = 0;
    virtual status_t        setBufferingSettings(const BufferingSettings& buffering) = 0;
    virtual status_t        prepareAsync() = 0;
    virtual status_t        start() = 0;
    virtual status_t        stop() = 0;
    virtual status_t        pause() = 0;
    virtual status_t        isPlaying(bool* state) = 0;
    virtual status_t        setPlaybackSettings(const AudioPlaybackRate& rate) = 0;
    virtual status_t        getPlaybackSettings(AudioPlaybackRate* rate /* nonnull */) = 0;
    virtual status_t        setSyncSettings(const AVSyncSettings& sync, float videoFpsHint) = 0;
    virtual status_t        getSyncSettings(AVSyncSettings* sync /* nonnull */,
                                            float* videoFps /* nonnull */) = 0;
    virtual status_t        seekTo(
            int msec,
            MediaPlayerSeekMode mode = MediaPlayerSeekMode::SEEK_PREVIOUS_SYNC) = 0;
    virtual status_t        getCurrentPosition(int* msec) = 0;
    virtual status_t        getDuration(int* msec) = 0;
    virtual status_t        notifyAt(int64_t mediaTimeUs) = 0;
    virtual status_t        reset() = 0;
    virtual status_t        setAudioStreamType(audio_stream_type_t type) = 0;
    virtual status_t        setLooping(int loop) = 0;
    virtual status_t        setVolume(float leftVolume, float rightVolume) = 0;
    virtual status_t        setAuxEffectSendLevel(float level) = 0;
    virtual status_t        attachAuxEffect(int effectId) = 0;
    virtual status_t        setParameter(int key, const Parcel& request) = 0;
    virtual status_t        getParameter(int key, Parcel* reply) = 0;
    virtual status_t        setRetransmitEndpoint(const struct sockaddr_in* endpoint) = 0;
    virtual status_t        getRetransmitEndpoint(struct sockaddr_in* endpoint) = 0;
    virtual status_t        setNextPlayer(const sp<IMediaPlayer>& next) = 0;

    virtual media::VolumeShaper::Status applyVolumeShaper(
                                    const sp<media::VolumeShaper::Configuration>& configuration,
                                    const sp<media::VolumeShaper::Operation>& operation) = 0;
    virtual sp<media::VolumeShaper::State> getVolumeShaperState(int id) = 0;

    // Modular DRM
    virtual status_t        prepareDrm(const uint8_t uuid[16],
                                    const Vector<uint8_t>& drmSessionId) = 0;
    virtual status_t        releaseDrm() = 0;

    // Invoke a generic method on the player by using opaque parcels
    // for the request and reply.
    // @param request Parcel that must start with the media player
    // interface token.
    // @param[out] reply Parcel to hold the reply data. Cannot be null.
    // @return OK if the invocation was made successfully.
    virtual status_t        invoke(const Parcel& request, Parcel *reply) = 0;

    // Set a new metadata filter.
    // @param filter A set of allow and drop rules serialized in a Parcel.
    // @return OK if the invocation was made successfully.
    virtual status_t        setMetadataFilter(const Parcel& filter) = 0;

    // Retrieve a set of metadata.
    // @param update_only Include only the metadata that have changed
    //                    since the last invocation of getMetadata.
    //                    The set is built using the unfiltered
    //                    notifications the native player sent to the
    //                    MediaPlayerService during that period of
    //                    time. If false, all the metadatas are considered.
    // @param apply_filter If true, once the metadata set has been built based
    //                     on the value update_only, the current filter is
    //                     applied.
    // @param[out] metadata On exit contains a set (possibly empty) of metadata.
    //                      Valid only if the call returned OK.
    // @return OK if the invocation was made successfully.
    virtual status_t        getMetadata(bool update_only,
                                        bool apply_filter,
                                        Parcel *metadata) = 0;

    // AudioRouting
    virtual status_t        setOutputDevice(audio_port_handle_t deviceId) = 0;
    virtual status_t        getRoutedDeviceId(audio_port_handle_t *deviceId) = 0;
    virtual status_t        enableAudioDeviceCallback(bool enabled) = 0;
};

// ----------------------------------------------------------------------------

class BnMediaPlayer: public BnInterface<IMediaPlayer>    //内部类
{
public:
    virtual status_t    onTransact( uint32_t code,
                                    const Parcel& data,
                                    Parcel* reply,
                                    uint32_t flags = 0);
};

11.回到MedaiPlayerService.cpp中 获取解码器列表方法   sp<IMediaCodecList> getCodecList() 

sp<IMediaCodecList> MediaPlayerService::getCodecList() const {
    return MediaCodecList::getLocalInstance();
}

///frameworks/av/media/libstagefright/MediaCodecList.cpp 中 getLocalInstance()

// static
sp<IMediaCodecList> MediaCodecList::getLocalInstance() {
    Mutex::Autolock autoLock(sInitMutex);

    if (sCodecList == nullptr) {
        MediaCodecList *codecList = new MediaCodecList(GetBuilders());
        if (codecList->initCheck() == OK) {
            sCodecList = codecList;

            if (isProfilingNeeded()) {
                ALOGV("Codec profiling needed, will be run in separated thread.");
                pthread_t profiler;
                if (pthread_create(&profiler, nullptr, profilerThreadWrapper, nullptr) != 0) {
                    ALOGW("Failed to create thread for codec profiling.");
                }
            }
        } else {
            // failure to initialize may be temporary. retry on next call.
            delete codecList;
        }
    }

    return sCodecList;
}

 

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值