• Home
  • History
  • Annotate
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1  //
2  //  Copyright 2015 Google, Inc.
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  #include "service/daemon.h"
18  
19  #include <memory>
20  
21  #include <base/logging.h>
22  #include <base/run_loop.h>
23  
24  #include "abstract_message_loop.h"
25  #include "service/adapter.h"
26  #include "service/hal/bluetooth_av_interface.h"
27  #include "service/hal/bluetooth_avrcp_interface.h"
28  #include "service/hal/bluetooth_gatt_interface.h"
29  #include "service/hal/bluetooth_interface.h"
30  #include "service/ipc/ipc_manager.h"
31  #include "service/settings.h"
32  #include "service/switches.h"
33  
34  namespace bluetooth {
35  
36  namespace {
37  
38  // The global Daemon instance.
39  Daemon* g_daemon = nullptr;
40  
41  class DaemonImpl : public Daemon, public ipc::IPCManager::Delegate {
42   public:
43    DaemonImpl() : initialized_(false) {}
44  
45    ~DaemonImpl() override {
46      if (!initialized_) return;
47  
48      CleanUpBluetoothStack();
49    }
50  
51    void StartMainLoop() override { base::RunLoop().Run(); }
52  
53    Settings* GetSettings() const override { return settings_.get(); }
54  
55    btbase::AbstractMessageLoop* GetMessageLoop() const override {
56      return message_loop_.get();
57    }
58  
59   private:
60    // ipc::IPCManager::Delegate implementation:
61    void OnIPCHandlerStarted(ipc::IPCManager::Type /* type */) override {
62      if (!settings_->EnableOnStart()) return;
63      adapter_->Enable();
64    }
65  
66    void OnIPCHandlerStopped(ipc::IPCManager::Type /* type */) override {
67      // Do nothing.
68    }
69  
70    bool StartUpBluetoothInterfaces() {
71      if (!hal::BluetoothInterface::Initialize()) goto failed;
72  
73      if (!hal::BluetoothGattInterface::Initialize()) goto failed;
74  
75      if (!hal::BluetoothAvInterface::Initialize()) goto failed;
76  
77      if (!hal::BluetoothAvrcpInterface::Initialize()) goto failed;
78  
79      return true;
80  
81    failed:
82      ShutDownBluetoothInterfaces();
83      return false;
84    }
85  
86    void ShutDownBluetoothInterfaces() {
87      if (hal::BluetoothGattInterface::IsInitialized())
88        hal::BluetoothGattInterface::CleanUp();
89      if (hal::BluetoothInterface::IsInitialized())
90        hal::BluetoothInterface::CleanUp();
91      if (hal::BluetoothAvInterface::IsInitialized())
92        hal::BluetoothAvInterface::CleanUp();
93      if (hal::BluetoothAvrcpInterface::IsInitialized())
94        hal::BluetoothAvrcpInterface::CleanUp();
95    }
96  
97    void CleanUpBluetoothStack() {
98      // The Adapter object needs to be cleaned up before the HAL interfaces.
99      ipc_manager_.reset();
100      adapter_.reset();
101      ShutDownBluetoothInterfaces();
102    }
103  
104    bool SetUpIPC() {
105      // If an IPC socket path was given, initialize IPC with it. Otherwise
106      // initialize Binder IPC.
107      if (settings_->UseSocketIPC()) {
108        if (!ipc_manager_->Start(ipc::IPCManager::TYPE_LINUX, this)) {
109          LOG(ERROR) << "Failed to set up UNIX domain-socket IPCManager";
110          return false;
111        }
112        return true;
113      }
114  
115  #if !defined(OS_GENERIC)
116      if (!ipc_manager_->Start(ipc::IPCManager::TYPE_BINDER, this)) {
117        LOG(ERROR) << "Failed to set up Binder IPCManager";
118        return false;
119      }
120  #else
121      if (!ipc_manager_->Start(ipc::IPCManager::TYPE_DBUS, this)) {
122        LOG(ERROR) << "Failed to set up DBus IPCManager";
123        return false;
124      }
125  #endif
126  
127      return true;
128    }
129  
130    bool Init() override {
131      CHECK(!initialized_);
132      message_loop_.reset(new btbase::AbstractMessageLoop());
133  
134      settings_.reset(new Settings());
135      if (!settings_->Init()) {
136        LOG(ERROR) << "Failed to set up Settings";
137        return false;
138      }
139  
140      if (!StartUpBluetoothInterfaces()) {
141        LOG(ERROR) << "Failed to set up HAL Bluetooth interfaces";
142        return false;
143      }
144  
145      adapter_ = Adapter::Create();
146      ipc_manager_.reset(new ipc::IPCManager(adapter_.get()));
147  
148      if (!SetUpIPC()) {
149        CleanUpBluetoothStack();
150        return false;
151      }
152  
153      initialized_ = true;
154      LOG(INFO) << "Daemon initialized";
155  
156      return true;
157    }
158  
159    bool initialized_;
160    std::unique_ptr<btbase::AbstractMessageLoop> message_loop_;
161    std::unique_ptr<Settings> settings_;
162    std::unique_ptr<Adapter> adapter_;
163    std::unique_ptr<ipc::IPCManager> ipc_manager_;
164  
165    DISALLOW_COPY_AND_ASSIGN(DaemonImpl);
166  };
167  
168  }  // namespace
169  
170  // static
171  bool Daemon::Initialize() {
172    CHECK(!g_daemon);
173  
174    g_daemon = new DaemonImpl();
175    if (g_daemon->Init()) return true;
176  
177    LOG(ERROR) << "Failed to initialize the Daemon object";
178  
179    delete g_daemon;
180    g_daemon = nullptr;
181  
182    return false;
183  }
184  
185  // static
186  void Daemon::ShutDown() {
187    CHECK(g_daemon);
188    delete g_daemon;
189    g_daemon = nullptr;
190  }
191  
192  // static
193  void Daemon::InitializeForTesting(Daemon* test_daemon) {
194    CHECK(test_daemon);
195    CHECK(!g_daemon);
196  
197    g_daemon = test_daemon;
198  }
199  
200  // static
201  Daemon* Daemon::Get() {
202    CHECK(g_daemon);
203    return g_daemon;
204  }
205  
206  }  // namespace bluetooth
207