13506f3f39a1328465009ec080a741373b338beadRakesh Iyer/* 23506f3f39a1328465009ec080a741373b338beadRakesh Iyer * Copyright (C) 2015 The Android Open Source Project 33506f3f39a1328465009ec080a741373b338beadRakesh Iyer * 43506f3f39a1328465009ec080a741373b338beadRakesh Iyer * Licensed under the Apache License, Version 2.0 (the "License"); 53506f3f39a1328465009ec080a741373b338beadRakesh Iyer * you may not use this file except in compliance with the License. 63506f3f39a1328465009ec080a741373b338beadRakesh Iyer * You may obtain a copy of the License at 73506f3f39a1328465009ec080a741373b338beadRakesh Iyer * 83506f3f39a1328465009ec080a741373b338beadRakesh Iyer * http://www.apache.org/licenses/LICENSE-2.0 93506f3f39a1328465009ec080a741373b338beadRakesh Iyer * 103506f3f39a1328465009ec080a741373b338beadRakesh Iyer * Unless required by applicable law or agreed to in writing, software 113506f3f39a1328465009ec080a741373b338beadRakesh Iyer * distributed under the License is distributed on an "AS IS" BASIS, 123506f3f39a1328465009ec080a741373b338beadRakesh Iyer * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 133506f3f39a1328465009ec080a741373b338beadRakesh Iyer * See the License for the specific language governing permissions and 143506f3f39a1328465009ec080a741373b338beadRakesh Iyer * limitations under the License. 153506f3f39a1328465009ec080a741373b338beadRakesh Iyer */ 163506f3f39a1328465009ec080a741373b338beadRakesh Iyerpackage com.android.car.systemupdater; 173506f3f39a1328465009ec080a741373b338beadRakesh Iyer 183506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport android.app.Activity; 193506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport android.app.AlertDialog; 203506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport android.app.FragmentManager; 213506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport android.app.ProgressDialog; 223506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport android.content.Context; 233506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport android.content.DialogInterface; 243506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport android.os.AsyncTask; 253506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport android.os.Bundle; 263506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport android.os.Handler; 273506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport android.os.RecoverySystem; 283506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport android.util.Log; 293506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport android.widget.Toast; 303506f3f39a1328465009ec080a741373b338beadRakesh Iyer 313506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport java.io.File; 323506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport java.io.FileInputStream; 333506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport java.io.FileOutputStream; 343506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport java.io.FilenameFilter; 353506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport java.io.IOException; 363506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport java.io.InputStream; 373506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport java.io.OutputStream; 383506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport java.security.GeneralSecurityException; 393506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport java.util.List; 403506f3f39a1328465009ec080a741373b338beadRakesh Iyer 413506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport android.os.storage.StorageEventListener; 423506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport android.os.storage.StorageManager; 433506f3f39a1328465009ec080a741373b338beadRakesh Iyerimport android.os.storage.VolumeInfo; 443506f3f39a1328465009ec080a741373b338beadRakesh Iyer 453506f3f39a1328465009ec080a741373b338beadRakesh Iyer/** 463506f3f39a1328465009ec080a741373b338beadRakesh Iyer * A prototype of performing system update using an ota package on internal or external storage. 473506f3f39a1328465009ec080a741373b338beadRakesh Iyer * TODO(yaochen): Move the code to a proper location and let it extend CarActivity once available. 483506f3f39a1328465009ec080a741373b338beadRakesh Iyer */ 493506f3f39a1328465009ec080a741373b338beadRakesh Iyerpublic class SystemUpdaterActivity extends Activity { 503506f3f39a1328465009ec080a741373b338beadRakesh Iyer private static final String TAG = "SystemUpdaterActivity"; 513506f3f39a1328465009ec080a741373b338beadRakesh Iyer private static final boolean DEBUG = true; 523506f3f39a1328465009ec080a741373b338beadRakesh Iyer private static final String UPDATE_FILE_NAME = "update.zip"; 533506f3f39a1328465009ec080a741373b338beadRakesh Iyer 543506f3f39a1328465009ec080a741373b338beadRakesh Iyer private final Handler mHandler = new Handler(); 553506f3f39a1328465009ec080a741373b338beadRakesh Iyer private StorageManager mStorageManager = null; 563506f3f39a1328465009ec080a741373b338beadRakesh Iyer private ProgressDialog mVerifyPackageDialog = null; 573506f3f39a1328465009ec080a741373b338beadRakesh Iyer 583506f3f39a1328465009ec080a741373b338beadRakesh Iyer 593506f3f39a1328465009ec080a741373b338beadRakesh Iyer private final StorageEventListener mListener = new StorageEventListener() { 603506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 613506f3f39a1328465009ec080a741373b338beadRakesh Iyer public void onVolumeStateChanged(VolumeInfo vol, int oldState, int newState) { 623506f3f39a1328465009ec080a741373b338beadRakesh Iyer if (DEBUG) { 633506f3f39a1328465009ec080a741373b338beadRakesh Iyer Log.d(TAG, "onVolumeMetadataChanged " + oldState + " " + newState 643506f3f39a1328465009ec080a741373b338beadRakesh Iyer + " " + vol.toString()); 653506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 663506f3f39a1328465009ec080a741373b338beadRakesh Iyer showMountedVolumes(); 673506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 683506f3f39a1328465009ec080a741373b338beadRakesh Iyer }; 693506f3f39a1328465009ec080a741373b338beadRakesh Iyer 703506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 713506f3f39a1328465009ec080a741373b338beadRakesh Iyer protected void onCreate(Bundle savedInstanceState) { 723506f3f39a1328465009ec080a741373b338beadRakesh Iyer super.onCreate(savedInstanceState); 733506f3f39a1328465009ec080a741373b338beadRakesh Iyer setContentView(R.layout.activity_main); 743506f3f39a1328465009ec080a741373b338beadRakesh Iyer mStorageManager = (StorageManager) getSystemService(Context.STORAGE_SERVICE); 753506f3f39a1328465009ec080a741373b338beadRakesh Iyer if (mStorageManager == null) { 763506f3f39a1328465009ec080a741373b338beadRakesh Iyer Log.w(TAG, "Failed to get StorageManager"); 773506f3f39a1328465009ec080a741373b338beadRakesh Iyer Toast.makeText(this, "Cannot get StorageManager!", Toast.LENGTH_LONG).show(); 783506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 793506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 803506f3f39a1328465009ec080a741373b338beadRakesh Iyer 813506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 823506f3f39a1328465009ec080a741373b338beadRakesh Iyer protected void onResume() { 833506f3f39a1328465009ec080a741373b338beadRakesh Iyer super.onResume(); 843506f3f39a1328465009ec080a741373b338beadRakesh Iyer if (mStorageManager != null) { 853506f3f39a1328465009ec080a741373b338beadRakesh Iyer mStorageManager.registerListener(mListener); 863506f3f39a1328465009ec080a741373b338beadRakesh Iyer showMountedVolumes(); 873506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 883506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 893506f3f39a1328465009ec080a741373b338beadRakesh Iyer 903506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 913506f3f39a1328465009ec080a741373b338beadRakesh Iyer protected void onPause() { 923506f3f39a1328465009ec080a741373b338beadRakesh Iyer super.onPause(); 933506f3f39a1328465009ec080a741373b338beadRakesh Iyer if (mStorageManager != null) { 943506f3f39a1328465009ec080a741373b338beadRakesh Iyer mStorageManager.unregisterListener(mListener); 953506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 963506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 973506f3f39a1328465009ec080a741373b338beadRakesh Iyer 983506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 993506f3f39a1328465009ec080a741373b338beadRakesh Iyer public void onBackPressed() { 1003506f3f39a1328465009ec080a741373b338beadRakesh Iyer if (getFragmentManager().getBackStackEntryCount() > 0) { 1013506f3f39a1328465009ec080a741373b338beadRakesh Iyer getFragmentManager().popBackStackImmediate(); 1023506f3f39a1328465009ec080a741373b338beadRakesh Iyer } else { 1033506f3f39a1328465009ec080a741373b338beadRakesh Iyer super.onBackPressed(); 1043506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 1053506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 1063506f3f39a1328465009ec080a741373b338beadRakesh Iyer 1073506f3f39a1328465009ec080a741373b338beadRakesh Iyer public void showMountedVolumes() { 1083506f3f39a1328465009ec080a741373b338beadRakesh Iyer if (mStorageManager == null) { 1093506f3f39a1328465009ec080a741373b338beadRakesh Iyer return; 1103506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 1113506f3f39a1328465009ec080a741373b338beadRakesh Iyer final List<VolumeInfo> vols = mStorageManager.getVolumes(); 1123506f3f39a1328465009ec080a741373b338beadRakesh Iyer File[] files = new File[vols.size()]; 1133506f3f39a1328465009ec080a741373b338beadRakesh Iyer int i = 0; 1143506f3f39a1328465009ec080a741373b338beadRakesh Iyer for (VolumeInfo vol : vols) { 1153506f3f39a1328465009ec080a741373b338beadRakesh Iyer File path = vol.getPathForUser(getUserId()); 1163506f3f39a1328465009ec080a741373b338beadRakesh Iyer if (vol.getState() != VolumeInfo.STATE_MOUNTED || path == null) { 1173506f3f39a1328465009ec080a741373b338beadRakesh Iyer continue; 1183506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 1193506f3f39a1328465009ec080a741373b338beadRakesh Iyer files[i++] = path; 1203506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 1213506f3f39a1328465009ec080a741373b338beadRakesh Iyer getFragmentManager().popBackStack(null, FragmentManager.POP_BACK_STACK_INCLUSIVE); 1223506f3f39a1328465009ec080a741373b338beadRakesh Iyer DeviceListFragment frag = new DeviceListFragment(); 1233506f3f39a1328465009ec080a741373b338beadRakesh Iyer frag.updateList(files); 1243506f3f39a1328465009ec080a741373b338beadRakesh Iyer frag.updateTitle(getString(R.string.title)); 1253506f3f39a1328465009ec080a741373b338beadRakesh Iyer getFragmentManager().beginTransaction() 1263506f3f39a1328465009ec080a741373b338beadRakesh Iyer .replace(R.id.device_container, frag).commit(); 1273506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 1283506f3f39a1328465009ec080a741373b338beadRakesh Iyer 1293506f3f39a1328465009ec080a741373b338beadRakesh Iyer public void showFolderContent(final File location) { 1303506f3f39a1328465009ec080a741373b338beadRakesh Iyer if (!location.isDirectory()) { 1313506f3f39a1328465009ec080a741373b338beadRakesh Iyer return; 1323506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 1333506f3f39a1328465009ec080a741373b338beadRakesh Iyer AsyncTask<String, Void, File[]> readFilesTask = new AsyncTask<String, Void, File[]>() { 1343506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 1353506f3f39a1328465009ec080a741373b338beadRakesh Iyer protected File[] doInBackground(String... strings) { 1363506f3f39a1328465009ec080a741373b338beadRakesh Iyer File f = new File(strings[0]); 1373506f3f39a1328465009ec080a741373b338beadRakesh Iyer /* if we want to filter files, use 1383506f3f39a1328465009ec080a741373b338beadRakesh Iyer File[] files = f.listFiles(new FilenameFilter() { 1393506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 1403506f3f39a1328465009ec080a741373b338beadRakesh Iyer public boolean accept(File dir, String filename) { 1413506f3f39a1328465009ec080a741373b338beadRakesh Iyer return true; 1423506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 1433506f3f39a1328465009ec080a741373b338beadRakesh Iyer }); */ 1443506f3f39a1328465009ec080a741373b338beadRakesh Iyer return f.listFiles(); 1453506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 1463506f3f39a1328465009ec080a741373b338beadRakesh Iyer 1473506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 1483506f3f39a1328465009ec080a741373b338beadRakesh Iyer protected void onPostExecute(File[] results) { 1493506f3f39a1328465009ec080a741373b338beadRakesh Iyer super.onPostExecute(results); 1503506f3f39a1328465009ec080a741373b338beadRakesh Iyer if (results == null) { 1513506f3f39a1328465009ec080a741373b338beadRakesh Iyer results = new File[0]; 1523506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 1533506f3f39a1328465009ec080a741373b338beadRakesh Iyer DeviceListFragment frag = new DeviceListFragment(); 1543506f3f39a1328465009ec080a741373b338beadRakesh Iyer frag.updateTitle(location.getAbsolutePath()); 1553506f3f39a1328465009ec080a741373b338beadRakesh Iyer frag.updateList(results); 1563506f3f39a1328465009ec080a741373b338beadRakesh Iyer getFragmentManager().beginTransaction() 1573506f3f39a1328465009ec080a741373b338beadRakesh Iyer .replace(R.id.device_container, frag).addToBackStack(null).commit(); 1583506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 1593506f3f39a1328465009ec080a741373b338beadRakesh Iyer }; 1603506f3f39a1328465009ec080a741373b338beadRakesh Iyer readFilesTask.execute(location.getAbsolutePath()); 1613506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 1623506f3f39a1328465009ec080a741373b338beadRakesh Iyer 1633506f3f39a1328465009ec080a741373b338beadRakesh Iyer public void checkPackage(File file) { 1643506f3f39a1328465009ec080a741373b338beadRakesh Iyer mVerifyPackageDialog = new ProgressDialog(this); 1653506f3f39a1328465009ec080a741373b338beadRakesh Iyer mVerifyPackageDialog.setTitle("Verifying... " + file.getAbsolutePath()); 1663506f3f39a1328465009ec080a741373b338beadRakesh Iyer 1673506f3f39a1328465009ec080a741373b338beadRakesh Iyer final PackageVerifier verifyPackage = new PackageVerifier(); 1683506f3f39a1328465009ec080a741373b338beadRakesh Iyer verifyPackage.execute(file); 1693506f3f39a1328465009ec080a741373b338beadRakesh Iyer mVerifyPackageDialog.setOnCancelListener(new DialogInterface.OnCancelListener() { 1703506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 1713506f3f39a1328465009ec080a741373b338beadRakesh Iyer public void onCancel(DialogInterface dialogInterface) { 1723506f3f39a1328465009ec080a741373b338beadRakesh Iyer verifyPackage.cancel(true); 1733506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 1743506f3f39a1328465009ec080a741373b338beadRakesh Iyer }); 1753506f3f39a1328465009ec080a741373b338beadRakesh Iyer mVerifyPackageDialog.setProgressStyle(mVerifyPackageDialog.STYLE_HORIZONTAL); 1763506f3f39a1328465009ec080a741373b338beadRakesh Iyer mVerifyPackageDialog.setMax(100); 1773506f3f39a1328465009ec080a741373b338beadRakesh Iyer mVerifyPackageDialog.setProgress(0); 1783506f3f39a1328465009ec080a741373b338beadRakesh Iyer mVerifyPackageDialog.show(); 1793506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 1803506f3f39a1328465009ec080a741373b338beadRakesh Iyer 1813506f3f39a1328465009ec080a741373b338beadRakesh Iyer private class PackageVerifier extends AsyncTask<File, Void, Exception> { 1823506f3f39a1328465009ec080a741373b338beadRakesh Iyer File mFile; 1833506f3f39a1328465009ec080a741373b338beadRakesh Iyer 1843506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 1853506f3f39a1328465009ec080a741373b338beadRakesh Iyer protected Exception doInBackground(File... files) { 1863506f3f39a1328465009ec080a741373b338beadRakesh Iyer File file = files[0]; 1873506f3f39a1328465009ec080a741373b338beadRakesh Iyer mFile = file; 1883506f3f39a1328465009ec080a741373b338beadRakesh Iyer try { 1893506f3f39a1328465009ec080a741373b338beadRakesh Iyer RecoverySystem.verifyPackage(file, mProgressListener, null); 1903506f3f39a1328465009ec080a741373b338beadRakesh Iyer } catch (GeneralSecurityException e) { 1913506f3f39a1328465009ec080a741373b338beadRakesh Iyer Log.e(TAG, "Security Exception in verifying package " + file, e); 1923506f3f39a1328465009ec080a741373b338beadRakesh Iyer return e; 1933506f3f39a1328465009ec080a741373b338beadRakesh Iyer } catch (IOException e) { 1943506f3f39a1328465009ec080a741373b338beadRakesh Iyer Log.e(TAG, "IO Exception in verifying package " + file, e); 1953506f3f39a1328465009ec080a741373b338beadRakesh Iyer return e; 1963506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 1973506f3f39a1328465009ec080a741373b338beadRakesh Iyer return null; 1983506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 1993506f3f39a1328465009ec080a741373b338beadRakesh Iyer 2003506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 2013506f3f39a1328465009ec080a741373b338beadRakesh Iyer protected void onPostExecute(Exception result) { 2023506f3f39a1328465009ec080a741373b338beadRakesh Iyer mVerifyPackageDialog.cancel(); 2033506f3f39a1328465009ec080a741373b338beadRakesh Iyer if (result == null) { 2043506f3f39a1328465009ec080a741373b338beadRakesh Iyer mVerifyPackageDialog = new ProgressDialog(SystemUpdaterActivity.this); 2053506f3f39a1328465009ec080a741373b338beadRakesh Iyer mVerifyPackageDialog.setTitle("Copying " + mFile.getName() 2063506f3f39a1328465009ec080a741373b338beadRakesh Iyer + " to " + getCacheDir() + "/" + UPDATE_FILE_NAME); 2073506f3f39a1328465009ec080a741373b338beadRakesh Iyer mVerifyPackageDialog.setProgressStyle(mVerifyPackageDialog.STYLE_HORIZONTAL); 2083506f3f39a1328465009ec080a741373b338beadRakesh Iyer mVerifyPackageDialog.setMax((int) (mFile.length() / 1024)); 2093506f3f39a1328465009ec080a741373b338beadRakesh Iyer mVerifyPackageDialog.show(); 2103506f3f39a1328465009ec080a741373b338beadRakesh Iyer new CopyFile().execute(mFile); 2113506f3f39a1328465009ec080a741373b338beadRakesh Iyer } else { 2123506f3f39a1328465009ec080a741373b338beadRakesh Iyer AlertDialog.Builder doneDialog = 2133506f3f39a1328465009ec080a741373b338beadRakesh Iyer new AlertDialog.Builder(SystemUpdaterActivity.this); 2143506f3f39a1328465009ec080a741373b338beadRakesh Iyer doneDialog.setMessage("Verification failed! " + result.getMessage()).show(); 2153506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 2163506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 2173506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 2183506f3f39a1328465009ec080a741373b338beadRakesh Iyer 2193506f3f39a1328465009ec080a741373b338beadRakesh Iyer 2203506f3f39a1328465009ec080a741373b338beadRakesh Iyer private class CopyFile extends AsyncTask<File, Void, Exception> { 2213506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 2223506f3f39a1328465009ec080a741373b338beadRakesh Iyer protected Exception doInBackground(File... files) { 2233506f3f39a1328465009ec080a741373b338beadRakesh Iyer File file = files[0]; 2243506f3f39a1328465009ec080a741373b338beadRakesh Iyer if (getCacheDir().getFreeSpace() < file.length()) { 2253506f3f39a1328465009ec080a741373b338beadRakesh Iyer return new IOException("Not enough cache space!"); 2263506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 2273506f3f39a1328465009ec080a741373b338beadRakesh Iyer File dest = new File(getCacheDir(), UPDATE_FILE_NAME); 2283506f3f39a1328465009ec080a741373b338beadRakesh Iyer try { 2293506f3f39a1328465009ec080a741373b338beadRakesh Iyer copy(file, dest); 2303506f3f39a1328465009ec080a741373b338beadRakesh Iyer } catch (IOException e) { 2313506f3f39a1328465009ec080a741373b338beadRakesh Iyer Log.e(TAG, "Error when coping file to cache", e); 2323506f3f39a1328465009ec080a741373b338beadRakesh Iyer dest.delete(); 2333506f3f39a1328465009ec080a741373b338beadRakesh Iyer return new IOException(e.getMessage()); 2343506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 2353506f3f39a1328465009ec080a741373b338beadRakesh Iyer return null; 2363506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 2373506f3f39a1328465009ec080a741373b338beadRakesh Iyer 2383506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 2393506f3f39a1328465009ec080a741373b338beadRakesh Iyer protected void onPostExecute(Exception result) { 2403506f3f39a1328465009ec080a741373b338beadRakesh Iyer mVerifyPackageDialog.cancel(); 2413506f3f39a1328465009ec080a741373b338beadRakesh Iyer AlertDialog.Builder doneDialog = new AlertDialog.Builder(SystemUpdaterActivity.this); 2423506f3f39a1328465009ec080a741373b338beadRakesh Iyer 2433506f3f39a1328465009ec080a741373b338beadRakesh Iyer doneDialog.setMessage("Copy " + (result == null ? "completed!" : "failed!" 2443506f3f39a1328465009ec080a741373b338beadRakesh Iyer + result.getMessage())); 2453506f3f39a1328465009ec080a741373b338beadRakesh Iyer 2463506f3f39a1328465009ec080a741373b338beadRakesh Iyer if (result == null) { 2473506f3f39a1328465009ec080a741373b338beadRakesh Iyer doneDialog.setPositiveButton("Start system update", 2483506f3f39a1328465009ec080a741373b338beadRakesh Iyer new DialogInterface.OnClickListener() { 2493506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 2503506f3f39a1328465009ec080a741373b338beadRakesh Iyer public void onClick(DialogInterface dialogInterface, int i) { 2513506f3f39a1328465009ec080a741373b338beadRakesh Iyer try { 2523506f3f39a1328465009ec080a741373b338beadRakesh Iyer RecoverySystem.installPackage(SystemUpdaterActivity.this, 2533506f3f39a1328465009ec080a741373b338beadRakesh Iyer new File(getCacheDir(), UPDATE_FILE_NAME)); 2543506f3f39a1328465009ec080a741373b338beadRakesh Iyer } catch (IOException e) { 2553506f3f39a1328465009ec080a741373b338beadRakesh Iyer Log.e(TAG, "IOException in installing ota package"); 2563506f3f39a1328465009ec080a741373b338beadRakesh Iyer Toast.makeText(SystemUpdaterActivity.this, 2573506f3f39a1328465009ec080a741373b338beadRakesh Iyer "IOException in installing ota package ", 2583506f3f39a1328465009ec080a741373b338beadRakesh Iyer Toast.LENGTH_LONG).show(); 2593506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 2603506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 2613506f3f39a1328465009ec080a741373b338beadRakesh Iyer }); 2623506f3f39a1328465009ec080a741373b338beadRakesh Iyer } else { 2633506f3f39a1328465009ec080a741373b338beadRakesh Iyer Log.e(TAG, "Copy failed!", result); 2643506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 2653506f3f39a1328465009ec080a741373b338beadRakesh Iyer doneDialog.create().show(); 2663506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 2673506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 2683506f3f39a1328465009ec080a741373b338beadRakesh Iyer 2693506f3f39a1328465009ec080a741373b338beadRakesh Iyer private void copy(File src, File dst) throws IOException { 2703506f3f39a1328465009ec080a741373b338beadRakesh Iyer InputStream in = new FileInputStream(src); 2713506f3f39a1328465009ec080a741373b338beadRakesh Iyer OutputStream out = new FileOutputStream(dst); 2723506f3f39a1328465009ec080a741373b338beadRakesh Iyer try { 2733506f3f39a1328465009ec080a741373b338beadRakesh Iyer // Transfer bytes from in to out 2743506f3f39a1328465009ec080a741373b338beadRakesh Iyer byte[] buf = new byte[0x10000]; // 64k 2753506f3f39a1328465009ec080a741373b338beadRakesh Iyer int len; 2763506f3f39a1328465009ec080a741373b338beadRakesh Iyer while ((len = in.read(buf)) > 0) { 2773506f3f39a1328465009ec080a741373b338beadRakesh Iyer out.write(buf, 0, len); 2783506f3f39a1328465009ec080a741373b338beadRakesh Iyer mHandler.post(new Runnable() { 2793506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 2803506f3f39a1328465009ec080a741373b338beadRakesh Iyer public void run() { 2813506f3f39a1328465009ec080a741373b338beadRakesh Iyer mVerifyPackageDialog.incrementProgressBy(1); 2823506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 2833506f3f39a1328465009ec080a741373b338beadRakesh Iyer }); 2843506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 2853506f3f39a1328465009ec080a741373b338beadRakesh Iyer } finally { 2863506f3f39a1328465009ec080a741373b338beadRakesh Iyer in.close(); 2873506f3f39a1328465009ec080a741373b338beadRakesh Iyer out.close(); 2883506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 2893506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 2903506f3f39a1328465009ec080a741373b338beadRakesh Iyer 2913506f3f39a1328465009ec080a741373b338beadRakesh Iyer private final RecoverySystem.ProgressListener mProgressListener = 2923506f3f39a1328465009ec080a741373b338beadRakesh Iyer new RecoverySystem.ProgressListener() { 2933506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 2943506f3f39a1328465009ec080a741373b338beadRakesh Iyer public void onProgress(final int i) { 2953506f3f39a1328465009ec080a741373b338beadRakesh Iyer mHandler.post(new Runnable() { 2963506f3f39a1328465009ec080a741373b338beadRakesh Iyer @Override 2973506f3f39a1328465009ec080a741373b338beadRakesh Iyer public void run() { 2983506f3f39a1328465009ec080a741373b338beadRakesh Iyer if (mVerifyPackageDialog != null) { 2993506f3f39a1328465009ec080a741373b338beadRakesh Iyer mVerifyPackageDialog.setProgress(i); 3003506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 3013506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 3023506f3f39a1328465009ec080a741373b338beadRakesh Iyer }); 3033506f3f39a1328465009ec080a741373b338beadRakesh Iyer } 3043506f3f39a1328465009ec080a741373b338beadRakesh Iyer }; 3053506f3f39a1328465009ec080a741373b338beadRakesh Iyer} 306