1 /*
2  * Copyright (C) 2015 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #ifndef ANDROID_HARDWARE_RADIO_SERVICE_H
18 #define ANDROID_HARDWARE_RADIO_SERVICE_H
19 
20 #include <utils/Vector.h>
21 //#include <binder/AppOpsManager.h>
22 #include <binder/MemoryDealer.h>
23 #include <binder/BinderService.h>
24 #include <binder/IAppOpsCallback.h>
25 #include <radio/IRadioService.h>
26 #include <radio/IRadio.h>
27 #include <radio/IRadioClient.h>
28 #include <system/radio.h>
29 #include <hardware/radio.h>
30 #include "RadioInterface.h"
31 #include "TunerInterface.h"
32 #include "TunerCallbackInterface.h"
33 
34 namespace android {
35 
36 class MemoryHeapBase;
37 
38 class RadioService :
39     public BinderService<RadioService>,
40     public BnRadioService
41 {
42     friend class BinderService<RadioService>;
43 
44 public:
45     class ModuleClient;
46     class Module;
47 
getServiceName()48     static char const* getServiceName() { return "media.radio"; }
49 
50                         RadioService();
51     virtual             ~RadioService();
52 
53     // IRadioService
54     virtual status_t listModules(struct radio_properties *properties,
55                                  uint32_t *numModules);
56 
57     virtual status_t attach(radio_handle_t handle,
58                             const sp<IRadioClient>& client,
59                             const struct radio_band_config *config,
60                             bool withAudio,
61                             sp<IRadio>& radio);
62 
63     virtual status_t    onTransact(uint32_t code, const Parcel& data,
64                                    Parcel* reply, uint32_t flags);
65 
66     virtual status_t    dump(int fd, const Vector<String16>& args);
67 
68 
69     class Module : public virtual RefBase {
70     public:
71 
72        Module(sp<RadioInterface> hwDevice,
73               struct radio_properties properties);
74 
75        virtual ~Module();
76 
77                sp<ModuleClient> addClient(const sp<IRadioClient>& client,
78                                   const struct radio_band_config *config,
79                                   bool audio);
80 
81                void removeClient(const sp<ModuleClient>& moduleClient);
82 
83                status_t setMute(bool mute);
84 
85                status_t getMute(bool *mute);
86 
87        virtual status_t dump(int fd, const Vector<String16>& args);
88 
hwDevice()89        sp<RadioInterface> hwDevice() const { return mHwDevice; }
properties()90        const struct radio_properties properties() const { return mProperties; }
91        const struct radio_band_config *getDefaultConfig() const ;
92 
93     private:
94 
95        void notifyDeviceConnection(bool connected, const char *address);
96 
97         Mutex                         mLock;          // protects  mModuleClients
98         sp<RadioInterface>            mHwDevice;      // HAL hardware device
99         const struct radio_properties mProperties;    // cached hardware module properties
100         Vector< sp<ModuleClient> >    mModuleClients; // list of attached clients
101         bool                          mMute;          // radio audio source state
102                                                       // when unmuted, audio is routed to the
103                                                       // output device selected for media use case.
104     }; // class Module
105 
106     class CallbackThread : public Thread {
107     public:
108 
109         explicit CallbackThread(const wp<ModuleClient>& moduleClient);
110 
111         virtual ~CallbackThread();
112 
113 
114         // Thread virtuals
115         virtual bool threadLoop();
116 
117         // RefBase
118         virtual void onFirstRef();
119 
120                 void exit();
121 
122                 void sendEvent(radio_hal_event_t *halEvent);
123                 sp<IMemory> prepareEvent(radio_hal_event_t *halEvent);
124 
125     private:
126         wp<ModuleClient>      mModuleClient;    // client module the thread belongs to
127         Condition             mCallbackCond;    // condition signaled when a new event is posted
128         Mutex                 mCallbackLock;    // protects mEventQueue
129         Vector< sp<IMemory> > mEventQueue;      // pending callback events
130         sp<MemoryDealer>      mMemoryDealer;    // shared memory for callback event
131     }; // class CallbackThread
132 
133     class ModuleClient : public BnRadio,
134                    public IBinder::DeathRecipient,
135                    public TunerCallbackInterface {
136     public:
137 
138        ModuleClient(const sp<Module>& module,
139               const sp<IRadioClient>& client,
140               const struct radio_band_config *config,
141               bool audio);
142 
143        virtual ~ModuleClient();
144 
145        // IRadio
146        virtual void detach();
147 
148        virtual status_t setConfiguration(const struct radio_band_config *config);
149 
150        virtual status_t getConfiguration(struct radio_band_config *config);
151 
152        virtual status_t setMute(bool mute);
153 
154        virtual status_t getMute(bool *mute);
155 
156        virtual status_t scan(radio_direction_t direction, bool skipSubChannel);
157 
158        virtual status_t step(radio_direction_t direction, bool skipSubChannel);
159 
160        virtual status_t tune(unsigned int channel, unsigned int subChannel);
161 
162        virtual status_t cancel();
163 
164        virtual status_t getProgramInformation(struct radio_program_info *info);
165 
166        virtual status_t hasControl(bool *hasControl);
167 
168        virtual status_t dump(int fd, const Vector<String16>& args);
169 
client()170                sp<IRadioClient> client() const { return mClient; }
module()171                wp<Module> module() const { return mModule; }
172                radio_hal_band_config_t halConfig() const;
callbackThread()173                sp<CallbackThread> callbackThread() const { return mCallbackThread; }
174                void setTuner(sp<TunerInterface>& tuner);
175                sp<TunerInterface>& getTuner();
audio()176                bool audio() const { return mAudio; }
177 
178                void onCallbackEvent(const sp<IMemory>& event);
179 
180        virtual void onFirstRef();
181 
182 
183        // IBinder::DeathRecipient implementation
184        virtual void        binderDied(const wp<IBinder> &who);
185 
186        // TunerCallbackInterface
187        virtual void onEvent(radio_hal_event_t *event);
188 
189     private:
190 
191         mutable Mutex               mLock;           // protects mClient, mConfig and mTuner
192         wp<Module>                  mModule;         // The module this client is attached to
193         sp<IRadioClient>            mClient;         // event callback binder interface
194         radio_band_config_t         mConfig;         // current band configuration
195         sp<CallbackThread>          mCallbackThread; // event callback thread
196         const bool                  mAudio;
197         sp<TunerInterface>          mTuner;        // HAL tuner interface. NULL indicates that
198                                                     // this client does not have control on any
199                                                     // tuner
200     }; // class ModuleClient
201 
202 
203     static void callback(radio_hal_event_t *halEvent, void *cookie);
204 
205 private:
206 
207     virtual void onFirstRef();
208 
209     static void convertProperties(radio_properties_t *properties,
210                                   const radio_hal_properties_t *halProperties);
211     Mutex               mServiceLock;   // protects mModules
212     volatile int32_t    mNextUniqueId;  // for module ID allocation
213     DefaultKeyedVector< radio_handle_t, sp<Module> > mModules;
214 };
215 
216 } // namespace android
217 
218 #endif // ANDROID_HARDWARE_RADIO_SERVICE_H
219