APP层
,
Framework层
,
Bluetooth.apk
三个部分。
开关是个SwitchBar,监听事件callback到onSwitchChanged,调用mLocalAdapter.setBluetoothEnabled(isChecked),mLocalAdapter是个com.android.settingslib.bluetooth.LocalBluetoothAdapter的一个实例:
public boolean enable() {
return mAdapter.enable();
}
这里的mAdapter是BluetoothAdapter的实例,在LocalBluetoothAdapter的构造函数中初始化。
@RequiresPermission(Manifest.permission.BLUETOOTH_ADMIN)
public boolean enable() {
android.util.SeempLog.record(56);
if (isEnabled()) {
if (DBG) Log.d(TAG, "enable(): BT already enabled!");
return true;
}
try {
return mManagerService.enable(ActivityThread.currentPackageName());
} catch (RemoteException e) {Log.e(TAG, "", e);}
return false;
}
private final IBluetoothManager mManagerService;
这个mManagerService是BluetoothManagerService的binder的代理。
public boolean enable(String packageName) throws RemoteException {
final int callingUid = Binder.getCallingUid();
final boolean callerSystem = UserHandle.getAppId(callingUid) == Process.SYSTEM_UID;
if (!callerSystem) {
if (!checkIfCallerIsForegroundUser()) {
Slog.w(TAG, "enable(): not allowed for non-active and non system user");
return false;
}
mContext.enforceCallingOrSelfPermission(BLUETOOTH_ADMIN_PERM,
"Need BLUETOOTH ADMIN permission");
if (!isEnabled() && mPermissionReviewRequired
&& startConsentUiIfNeeded(packageName, callingUid,
BluetoothAdapter.ACTION_REQUEST_ENABLE)) {
return false;
}
}
if (DBG) {
Slog.d(TAG,"enable(" + packageName + "): mBluetooth =" + mBluetooth +
" mBinding = " + mBinding + " mState = " +
BluetoothAdapter.nameForState(mState));
}
synchronized(mReceiver) {
mQuietEnableExternal = false;
mEnableExternal = true;
// waive WRITE_SECURE_SETTINGS permission check
sendEnableMsg(false, packageName);
}
if (DBG) Slog.d(TAG, "enable returning");
return true;
}
先是做一些权限检查,然后:
private void sendEnableMsg(boolean quietMode, String packageName) {
mHandler.sendMessage(mHandler.obtainMessage(MESSAGE_ENABLE,
quietMode ? 1 : 0, 0));
addActiveLog(packageName, true);
}
看看Handler里怎么处理MESSAGE_ENABLE消息:
case MESSAGE_ENABLE:
if (DBG) {
Slog.d(TAG, "MESSAGE_ENABLE(" + msg.arg1 + "): mBluetooth = " + mBluetooth);
}
mHandler.removeMessages(MESSAGE_RESTART_BLUETOOTH_SERVICE);
mEnable = true;
// Use service interface to get the exact state
try {
mBluetoothLock.readLock().lock();
if (mBluetooth != null) {
int state = mBluetooth.getState();
if (state == BluetoothAdapter.STATE_BLE_ON) {
Slog.w(TAG, "BT Enable in BLE_ON State, going to ON");
mBluetooth.onLeServiceUp();
// waive WRITE_SECURE_SETTINGS permission check
long callingIdentity = Binder.clearCallingIdentity();
persistBluetoothSetting(BLUETOOTH_ON_BLUETOOTH);
Binder.restoreCallingIdentity(callingIdentity);
break;
}
}
} catch (RemoteException e) {
Slog.e(TAG, "", e);
} finally {
mBluetoothLock.readLock().unlock();
}
mQuietEnable = (msg.arg1 == 1);
if (mBluetooth == null) {
handleEnable(mQuietEnable);
} else {
int state;
try {
state = mBluetooth.getState();
} catch (RemoteException e) {
Slog.e(TAG, "getState()", e);
break;
}
if(state == BluetoothAdapter.STATE_TURNING_OFF || state == BluetoothAdapter.STATE_BLE_TURNING_OFF)
waitForMonitoredOnOff(false, true);
Message restartMsg = mHandler.obtainMessage(
MESSAGE_RESTART_BLUETOOTH_SERVICE);
mHandler.sendMessageDelayed(restartMsg, 2 * SERVICE_RESTART_TIME_MS);
}
break;
mBluetooth是IBluetooth类型的实例,IBluetooth是aidl,由AdapterService里的内部类AdapterServiceBinder继承实现,AdapterService是Bluetooth.apk里的类。如果支持BLE,那此时mBluetooth.getState()的返回值是BluetoothAdapter.STATE_BLE_ON, 所以下一步走到onLeServiceUp:
public void onLeServiceUp() {
Message m = mAdapterStateMachine.obtainMessage(AdapterState.USER_TURN_ON);
mAdapterStateMachine.sendMessage(m);
}
mAdapterStateMachine是AdapterState的实例, AdapterState是个状态机,继承自com.android.internal.util.StateMachine(对状态机有兴趣的请看我前面的博客,有三篇详细讲解状态机)。
所以发的消息USER_TURN_ON就要看目前是在哪个状态,便在哪个状态处理这个消息。
打开蓝牙,enable()前便已进入BleOnState状态,所以USER_TURN_ON消息也在此状态中处理:
case USER_TURN_ON:
notifyAdapterStateChange(BluetoothAdapter.STATE_TURNING_ON);
adapterProperties.clearDisableFlag();
mPendingCommandState.setTurningOn(true);
transitionTo(mPendingCommandState);
sendMessageDelayed(BREDR_START_TIMEOUT, BREDR_START_TIMEOUT_DELAY);
adapterService.startCoreServices();
break;
可以看到进入了PendingCommandState状态,且adapterService.startCoreServices() :
void startCoreServices()
{
debugLog("startCoreServices()");
Class[] supportedProfileServices = Config.getSupportedProfiles();
//Start profile services
if (!mProfilesStarted && supportedProfileServices.length >0) {
//Startup all profile services
setProfileServiceState(supportedProfileServices,BluetoothAdapter.STATE_ON);
}else {
Log.w(TAG,"startCoreProfiles(): Profile Services alreay started");
mAdapterStateMachine.sendMessage(mAdapterStateMachine.obtainMessage(AdapterState.BREDR_STARTED));
}
}
其中Config.getSupportedProfiles()获取的是Config类中的SUPPORTED_PROFILES
, 该变量的值在上一篇的讲bluetooth_jni的博客中顺带提过,在打开蓝牙,拉起Bluetooth进程,第一个会执行的可见方法中便会初始化且赋值,里面放的是支持的协议List。这里面包含了BLE的协议和传统蓝牙的协议,具体支持哪些协议在这里配置:packages/apps/Bluetooth/res/values/config.xml
。
知道了支持的协议,便是一个一个拉起各个service:
@SuppressWarnings("rawtypes")
private void setProfileServiceState(Class[] services, int state) {
if (state != BluetoothAdapter.STATE_ON && state != BluetoothAdapter.STATE_OFF) {
debugLog("setProfileServiceState() - Invalid state, leaving...");
return;
}
int expectedCurrentState= BluetoothAdapter.STATE_OFF;
int pendingState = BluetoothAdapter.STATE_TURNING_ON;
if (state == BluetoothAdapter.STATE_OFF) {
expectedCurrentState= BluetoothAdapter.STATE_ON;
pendingState = BluetoothAdapter.STATE_TURNING_OFF;
}
Log.w(TAG, "Total profiles ="+ (services.length));
for (int i=0; i <services.length;i++) {
String serviceName = services[i].getName();
String simpleName = services[i].getSimpleName();
if (simpleName.equals("GattService")) continue;
Integer serviceState = mProfileServicesState.get(serviceName);
if(serviceState != null && serviceState != expectedCurrentState) {
Log.w(TAG, "setProfileServiceState() - Unable to "
+ (state == BluetoothAdapter.STATE_OFF ? "start" : "stop" )
+ " service " + serviceName
+ ". Invalid state: " + serviceState);
continue;
}
Log.w(TAG, "setProfileServiceState() - "
+ (state == BluetoothAdapter.STATE_OFF ? "Stopping" : "Starting")
+ " service " + serviceName);
mProfileServicesState.put(serviceName,pendingState);
Intent intent = new Intent(this,services[i]);
intent.putExtra(EXTRA_ACTION,ACTION_SERVICE_STATE_CHANGED);
intent.putExtra(BluetoothAdapter.EXTRA_STATE,state);
intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
startService(intent);
}
}
进入各个协议的service后都进入listen状态,看是不是有设备要连接自己,比如有设备要传输音频过来,要先连接我方的OPP协议,那么这时我方OPP协议才能知道设备要连自己。这属于协议栈的分析,其中的代码流程分析不在此篇wiki中。
当在APP层enable蓝牙的流程就这样。