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 */
16package com.android.settings.applications;
17
18import static android.net.NetworkPolicyManager.POLICY_NONE;
19import static android.net.NetworkPolicyManager.POLICY_REJECT_METERED_BACKGROUND;
20
21import android.app.ActivityManager;
22import android.app.AlertDialog;
23import android.app.AppOpsManager;
24import android.app.INotificationManager;
25import android.content.Context;
26import android.content.DialogInterface;
27import android.content.pm.ApplicationInfo;
28import android.content.pm.IPackageManager;
29import android.content.pm.PackageManager;
30import android.net.NetworkPolicyManager;
31import android.os.AsyncTask;
32import android.os.Bundle;
33import android.os.RemoteException;
34import android.os.ServiceManager;
35import android.os.UserHandle;
36
37import com.android.settings.R;
38
39import java.util.List;
40
41public class ResetAppsHelper implements DialogInterface.OnClickListener,
42        DialogInterface.OnDismissListener {
43
44    private static final String EXTRA_RESET_DIALOG = "resetDialog";
45
46    private final PackageManager mPm;
47    private final IPackageManager mIPm;
48    private final INotificationManager mNm;
49    private final NetworkPolicyManager mNpm;
50    private final AppOpsManager mAom;
51    private final Context mContext;
52
53    private AlertDialog mResetDialog;
54
55    public ResetAppsHelper(Context context) {
56        mContext = context;
57        mPm = context.getPackageManager();
58        mIPm = IPackageManager.Stub.asInterface(ServiceManager.getService("package"));
59        mNm = INotificationManager.Stub.asInterface(
60                ServiceManager.getService(Context.NOTIFICATION_SERVICE));
61        mNpm = NetworkPolicyManager.from(context);
62        mAom = (AppOpsManager) context.getSystemService(Context.APP_OPS_SERVICE);
63    }
64
65    public void onRestoreInstanceState(Bundle savedInstanceState) {
66        if (savedInstanceState != null && savedInstanceState.getBoolean(EXTRA_RESET_DIALOG)) {
67            buildResetDialog();
68        }
69    }
70
71    public void onSaveInstanceState(Bundle outState) {
72        if (mResetDialog != null) {
73            outState.putBoolean(EXTRA_RESET_DIALOG, true);
74        }
75    }
76
77    public void stop() {
78        if (mResetDialog != null) {
79            mResetDialog.dismiss();
80            mResetDialog = null;
81        }
82    }
83
84    void buildResetDialog() {
85        if (mResetDialog == null) {
86            mResetDialog = new AlertDialog.Builder(mContext)
87                    .setTitle(R.string.reset_app_preferences_title)
88                    .setMessage(R.string.reset_app_preferences_desc)
89                    .setPositiveButton(R.string.reset_app_preferences_button, this)
90                    .setNegativeButton(R.string.cancel, null)
91                    .setOnDismissListener(this)
92                    .show();
93        }
94    }
95
96    @Override
97    public void onDismiss(DialogInterface dialog) {
98        if (mResetDialog == dialog) {
99            mResetDialog = null;
100        }
101    }
102
103    @Override
104    public void onClick(DialogInterface dialog, int which) {
105        if (mResetDialog != dialog) {
106            return;
107        }
108        AsyncTask.execute(new Runnable() {
109            @Override
110            public void run() {
111                List<ApplicationInfo> apps = mPm.getInstalledApplications(
112                        PackageManager.GET_DISABLED_COMPONENTS);
113                for (int i = 0; i < apps.size(); i++) {
114                    ApplicationInfo app = apps.get(i);
115                    try {
116                        mNm.setNotificationsEnabledForPackage(app.packageName, app.uid, true);
117                    } catch (android.os.RemoteException ex) {
118                    }
119                    if (!app.enabled) {
120                        if (mPm.getApplicationEnabledSetting(app.packageName)
121                                == PackageManager.COMPONENT_ENABLED_STATE_DISABLED_USER) {
122                            mPm.setApplicationEnabledSetting(app.packageName,
123                                    PackageManager.COMPONENT_ENABLED_STATE_DEFAULT,
124                                    PackageManager.DONT_KILL_APP);
125                        }
126                    }
127                }
128                try {
129                    mIPm.resetApplicationPreferences(UserHandle.myUserId());
130                } catch (RemoteException e) {
131                }
132                mAom.resetAllModes();
133                final int[] restrictedUids = mNpm.getUidsWithPolicy(
134                        POLICY_REJECT_METERED_BACKGROUND);
135                final int currentUserId = ActivityManager.getCurrentUser();
136                for (int uid : restrictedUids) {
137                    // Only reset for current user
138                    if (UserHandle.getUserId(uid) == currentUserId) {
139                        mNpm.setUidPolicy(uid, POLICY_NONE);
140                    }
141                }
142            }
143        });
144    }
145}
146