Home | History | Annotate | Download | only in vpndialogs
      1 /*
      2  * Copyright (C) 2011 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  */
     16 
     17 package com.android.vpndialogs;
     18 
     19 import android.app.Activity;
     20 import android.app.AlertDialog;
     21 import android.content.Context;
     22 import android.content.DialogInterface;
     23 import android.content.Intent;
     24 import android.content.pm.ApplicationInfo;
     25 import android.content.pm.PackageManager;
     26 import android.net.IConnectivityManager;
     27 import android.os.Handler;
     28 import android.os.Message;
     29 import android.os.ServiceManager;
     30 import android.os.SystemClock;
     31 import android.util.Log;
     32 import android.view.View;
     33 import android.widget.Button;
     34 import android.widget.CompoundButton;
     35 import android.widget.ImageView;
     36 import android.widget.TextView;
     37 
     38 import com.android.internal.net.VpnConfig;
     39 
     40 import java.io.DataInputStream;
     41 import java.io.FileInputStream;
     42 
     43 public class ManageDialog extends Activity implements Handler.Callback,
     44         DialogInterface.OnClickListener, DialogInterface.OnDismissListener {
     45     private static final String TAG = "VpnManage";
     46 
     47     private VpnConfig mConfig;
     48 
     49     private IConnectivityManager mService;
     50 
     51     private AlertDialog mDialog;
     52     private TextView mDuration;
     53     private TextView mDataTransmitted;
     54     private TextView mDataReceived;
     55 
     56     private Handler mHandler;
     57 
     58     @Override
     59     protected void onResume() {
     60         super.onResume();
     61 
     62         if (getCallingPackage() != null) {
     63             Log.e(TAG, getCallingPackage() + " cannot start this activity");
     64             finish();
     65             return;
     66         }
     67 
     68         try {
     69             mConfig = getIntent().getParcelableExtra("config");
     70 
     71             mService = IConnectivityManager.Stub.asInterface(
     72                     ServiceManager.getService(Context.CONNECTIVITY_SERVICE));
     73 
     74             View view = View.inflate(this, R.layout.manage, null);
     75             if (mConfig.session != null) {
     76                 ((TextView) view.findViewById(R.id.session)).setText(mConfig.session);
     77             }
     78             mDuration = (TextView) view.findViewById(R.id.duration);
     79             mDataTransmitted = (TextView) view.findViewById(R.id.data_transmitted);
     80             mDataReceived = (TextView) view.findViewById(R.id.data_received);
     81 
     82             if (mConfig.user.equals(VpnConfig.LEGACY_VPN)) {
     83                 mDialog = new AlertDialog.Builder(this)
     84                         .setIcon(android.R.drawable.ic_dialog_info)
     85                         .setTitle(R.string.legacy_title)
     86                         .setView(view)
     87                         .setNeutralButton(R.string.disconnect, this)
     88                         .setNegativeButton(android.R.string.cancel, this)
     89                         .create();
     90             } else {
     91                 PackageManager pm = getPackageManager();
     92                 ApplicationInfo app = pm.getApplicationInfo(mConfig.user, 0);
     93                 mDialog = new AlertDialog.Builder(this)
     94                         .setIcon(app.loadIcon(pm))
     95                         .setTitle(app.loadLabel(pm))
     96                         .setView(view)
     97                         .setNeutralButton(R.string.disconnect, this)
     98                         .setNegativeButton(android.R.string.cancel, this)
     99                         .create();
    100             }
    101 
    102             if (mConfig.configureIntent != null) {
    103                 mDialog.setButton(DialogInterface.BUTTON_POSITIVE,
    104                         getText(R.string.configure), this);
    105             }
    106             mDialog.setOnDismissListener(this);
    107             mDialog.show();
    108 
    109             if (mHandler == null) {
    110                 mHandler = new Handler(this);
    111             }
    112             mHandler.sendEmptyMessage(0);
    113         } catch (Exception e) {
    114             Log.e(TAG, "onResume", e);
    115             finish();
    116         }
    117     }
    118 
    119     @Override
    120     protected void onPause() {
    121         super.onPause();
    122         if (mDialog != null) {
    123             mDialog.setOnDismissListener(null);
    124             mDialog.dismiss();
    125         }
    126     }
    127 
    128     @Override
    129     public void onClick(DialogInterface dialog, int which) {
    130         try {
    131             if (which == AlertDialog.BUTTON_POSITIVE) {
    132                 mConfig.configureIntent.send();
    133             } else if (which == AlertDialog.BUTTON_NEUTRAL) {
    134                 mService.prepareVpn(mConfig.user, VpnConfig.LEGACY_VPN);
    135             }
    136         } catch (Exception e) {
    137             Log.e(TAG, "onClick", e);
    138             finish();
    139         }
    140     }
    141 
    142     @Override
    143     public void onDismiss(DialogInterface dialog) {
    144         finish();
    145     }
    146 
    147     @Override
    148     public boolean handleMessage(Message message) {
    149         mHandler.removeMessages(0);
    150 
    151         if (mDialog.isShowing()) {
    152             if (mConfig.startTime != 0) {
    153                 long seconds = (SystemClock.elapsedRealtime() - mConfig.startTime) / 1000;
    154                 mDuration.setText(String.format("%02d:%02d:%02d",
    155                         seconds / 3600, seconds / 60 % 60, seconds % 60));
    156             }
    157 
    158             String[] numbers = getStatistics();
    159             if (numbers != null) {
    160                 // [1] and [2] are received data in bytes and packets.
    161                 mDataReceived.setText(getString(R.string.data_value_format,
    162                         numbers[1], numbers[2]));
    163 
    164                 // [9] and [10] are transmitted data in bytes and packets.
    165                 mDataTransmitted.setText(getString(R.string.data_value_format,
    166                         numbers[9], numbers[10]));
    167             }
    168             mHandler.sendEmptyMessageDelayed(0, 1000);
    169         }
    170         return true;
    171     }
    172 
    173     private String[] getStatistics() {
    174         DataInputStream in = null;
    175         try {
    176             // See dev_seq_printf_stats() in net/core/dev.c.
    177             in = new DataInputStream(new FileInputStream("/proc/net/dev"));
    178             String prefix = mConfig.interfaze + ':';
    179 
    180             while (true) {
    181                 String line = in.readLine().trim();
    182                 if (line.startsWith(prefix)) {
    183                     String[] numbers = line.substring(prefix.length()).split(" +");
    184                     for (int i = 1; i < 17; ++i) {
    185                         if (!numbers[i].equals("0")) {
    186                             return numbers;
    187                         }
    188                     }
    189                     break;
    190                 }
    191             }
    192         } catch (Exception e) {
    193             // ignore
    194         } finally {
    195             try {
    196                 in.close();
    197             } catch (Exception e) {
    198                 // ignore
    199             }
    200         }
    201         return null;
    202     }
    203 }
    204