CarEnrolmentActivity.java revision 77e5e49cf9dcceb69b07510c380ae2a9285ebfee
1/* 2 * Copyright (C) 2017 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 */ 16package com.android.car.trust; 17 18import android.app.Activity; 19import android.bluetooth.BluetoothDevice; 20import android.content.BroadcastReceiver; 21import android.content.ComponentName; 22import android.content.Context; 23import android.content.Intent; 24import android.content.IntentFilter; 25import android.content.ServiceConnection; 26import android.content.SharedPreferences; 27import android.os.Bundle; 28import android.os.IBinder; 29import android.os.RemoteException; 30import android.preference.PreferenceManager; 31import android.support.v4.content.LocalBroadcastManager; 32import android.util.Log; 33import android.view.View; 34import android.widget.Button; 35import android.widget.TextView; 36import com.android.car.trust.CarEnrolmentService.EnrolmentCallback; 37import com.android.car.trust.comms.SimpleBleServer.ConnectionListener; 38 39import static com.android.car.trust.CarBleTrustAgent.ACTION_ADD_TOKEN_RESULT; 40import static com.android.car.trust.CarBleTrustAgent.ACTION_TOKEN_STATUS_RESULT; 41import static com.android.car.trust.CarBleTrustAgent.INTENT_EXTRA_TOKEN_HANDLE; 42import static com.android.car.trust.CarBleTrustAgent.INTENT_EXTRA_TOKEN_STATUS; 43 44/** 45 * Setup activity that binds {@link CarEnrolmentService} and starts the enrolment process. 46 */ 47public class CarEnrolmentActivity extends Activity { 48 private static String TAG = "CarEnrolment"; 49 private static String SP_HANDLE_KEY = "sp-test"; 50 51 private TextView mOutputText; 52 private TextView mStartButton; 53 54 private long mHandle; 55 56 private CarEnrolmentService mEnrolmentService; 57 58 private BluetoothDevice mDevice; 59 60 private boolean mServiceBound; 61 62 private LocalBroadcastManager mLocalBroadcastManager; 63 64 private SharedPreferences mPrefs; 65 66 private final BroadcastReceiver mReceiver = new BroadcastReceiver() { 67 @Override 68 public void onReceive(Context context, Intent intent) { 69 intent.getPackage(); 70 71 String action = intent.getAction(); 72 Log.d(TAG, "Received broadcast: " + action); 73 if (ACTION_TOKEN_STATUS_RESULT.equals(action)) { 74 boolean tokenActive = intent.getBooleanExtra(INTENT_EXTRA_TOKEN_STATUS, false); 75 appendOutputText("Is token active? " + tokenActive + " handle: " + mHandle); 76 } else if (ACTION_ADD_TOKEN_RESULT.equals(action)) { 77 final long handle = intent.getLongExtra(INTENT_EXTRA_TOKEN_HANDLE, -1); 78 79 runOnUiThread(new Runnable() { 80 @Override 81 public void run() { 82 Log.d(TAG, "about to store new handle"); 83 mPrefs.edit().putLong(SP_HANDLE_KEY, handle).apply(); 84 Log.d(TAG, "stored new handle"); 85 } 86 }); 87 88 mEnrolmentService.sendHandle(handle, mDevice); 89 appendOutputText("Escrow Token Added. Handle: " + handle 90 + "\nLock and unlock the device to activate token"); 91 } 92 } 93 }; 94 95 @Override 96 protected void onCreate(Bundle savedInstanceState) { 97 super.onCreate(savedInstanceState); 98 99 setContentView(R.layout.car_client); 100 mOutputText = (TextView) findViewById(R.id.textfield); 101 102 final Intent intent = new Intent(this, CarEnrolmentService.class); 103 104 mPrefs = PreferenceManager.getDefaultSharedPreferences(this /* context */); 105 106 IntentFilter filter = new IntentFilter(); 107 filter.addAction(ACTION_TOKEN_STATUS_RESULT); 108 filter.addAction(ACTION_ADD_TOKEN_RESULT); 109 110 mLocalBroadcastManager = LocalBroadcastManager.getInstance(this /* context */); 111 mLocalBroadcastManager.registerReceiver(mReceiver, filter); 112 113 mStartButton = (Button) findViewById(R.id.start_button); 114 mStartButton.setOnClickListener(new View.OnClickListener() { 115 @Override 116 public void onClick(View v) { 117 // binding the service will start it if not started. 118 bindService(intent, mServiceConnection, Context.BIND_AUTO_CREATE); 119 } 120 }); 121 122 Button revokeButton = (Button) findViewById(R.id.revoke_trust_button); 123 revokeButton.setOnClickListener(new View.OnClickListener() { 124 @Override 125 public void onClick(View v) { 126 Intent intent = new Intent(CarBleTrustAgent.ACTION_REVOKE_TRUST); 127 intent.setPackage(getPackageName()); 128 sendBroadcast(intent); 129 } 130 }); 131 } 132 133 private ServiceConnection mServiceConnection = new ServiceConnection() { 134 public void onServiceConnected(ComponentName className, 135 IBinder service) { 136 mServiceBound = true; 137 CarEnrolmentService.EnrolmentServiceBinder binder 138 = (CarEnrolmentService.EnrolmentServiceBinder) service; 139 mEnrolmentService = binder.getService(); 140 mEnrolmentService.addEnrolmentCallback(mEnrolmentCallback); 141 mEnrolmentService.addConnectionListener(mConnectionListener); 142 mEnrolmentService.start(); 143 } 144 145 public void onServiceDisconnected(ComponentName arg0) { 146 mEnrolmentService = null; 147 mServiceBound = false; 148 } 149 }; 150 151 @Override 152 public void onResume() { 153 super.onResume(); 154 155 if (!mPrefs.contains(SP_HANDLE_KEY)) { 156 appendOutputText("No handles found."); 157 return; 158 } 159 160 try { 161 mHandle = mPrefs.getLong(SP_HANDLE_KEY, -1); 162 Log.d(TAG, "onResume, checking handle active: " + mHandle); 163 isTokenActive(mHandle); 164 } catch (RemoteException e) { 165 Log.e(TAG, "Error checking if token is valid"); 166 appendOutputText("Error checking if token is valid"); 167 } 168 } 169 170 @Override 171 public void onDestroy() { 172 if (mServiceBound) { 173 unbindService(mServiceConnection); 174 } 175 super.onDestroy(); 176 } 177 178 private void appendOutputText(final String text) { 179 runOnUiThread(new Runnable() { 180 @Override 181 public void run() { 182 mOutputText.append("\n" + text); 183 } 184 }); 185 } 186 187 private ConnectionListener mConnectionListener = new ConnectionListener() { 188 @Override 189 public void onServerStarted() { 190 appendOutputText("Server started"); 191 } 192 193 @Override 194 public void onServerStartFailed(int errorCode) { 195 appendOutputText("Server failed to start, error code: " + errorCode); 196 } 197 198 @Override 199 public void onDeviceConnected(BluetoothDevice device) { 200 mDevice = device; 201 appendOutputText("Device connected: " + device.getName() 202 + " addr: " + device.getAddress()); 203 } 204 }; 205 206 private EnrolmentCallback mEnrolmentCallback = new EnrolmentCallback() { 207 @Override 208 public void onEnrolmentDataReceived(byte[] token) { 209 appendOutputText("Enrolment data received "); 210 addEscrowToken(token); 211 } 212 }; 213 214 private void isTokenActive(long handle) throws RemoteException { 215 Intent intent = new Intent(); 216 intent.setAction(CarBleTrustAgent.ACTION_IS_TOKEN_ACTIVE); 217 intent.putExtra(CarBleTrustAgent.INTENT_EXTRA_TOKEN_HANDLE, handle); 218 219 mLocalBroadcastManager.sendBroadcast(intent); 220 } 221 222 private void addEscrowToken(byte[] token) { 223 long handle; 224 225 if (mPrefs.contains(SP_HANDLE_KEY)) { 226 handle = mPrefs.getLong(SP_HANDLE_KEY, -1); 227 appendOutputText("Removing old token, handle value: " + handle); 228 Intent intent = new Intent(); 229 intent.setAction(CarBleTrustAgent.ACTION_REMOVE_TOKEN); 230 intent.putExtra(CarBleTrustAgent.INTENT_EXTRA_TOKEN_HANDLE, handle); 231 mLocalBroadcastManager.sendBroadcast(intent); 232 } 233 234 Intent intent = new Intent(); 235 intent.setAction(CarBleTrustAgent.ACTION_ADD_TOKEN); 236 intent.putExtra(CarBleTrustAgent.INTENT_EXTRA_ESCROW_TOKEN, token); 237 238 mLocalBroadcastManager.sendBroadcast(intent); 239 } 240} 241