Search in sources :

Example 1 with Sample

use of edu.berkeley.cs.amplab.carat.thrift.Sample in project carat by amplab.

the class SamplerService method getSample.

/**
     * Takes a Sample and stores it in the database. Does not store the first ever samples 
     * that have no battery info.
     * @param context from onReceive
     * @param intent from onReceive
     * @return the newly recorded Sample
     */
private void getSample(Context context, Intent intent, Sample lastSample, CaratSampleDB sampleDB) {
    // String action = intent.getStringExtra("OriginalAction");
    // Log.i("SamplerService.getSample()", "Original intent: " +action);
    String lastBatteryState = lastSample != null ? lastSample.getBatteryState() : "Unknown";
    Sample s = SamplingLibrary.getSample(context, intent, lastBatteryState);
    // Set distance to current distance value
    if (s != null) {
        s.setDistanceTraveled(distance);
        // FIX: Do not use same distance again.
        distance = 0;
    }
    // But only after first real numbers
    if (!s.getBatteryState().equals("Unknown") && s.getBatteryLevel() >= 0) {
        // store the sample into the database
        long id = sampleDB.putSample(s);
        Log.i(TAG, "Took sample " + id + " for " + intent.getAction());
    //FlurryAgent.logEvent(intent.getAction());
    //  Log.d(TAG, "current battery level (just before quitting getSample() ): " + SamplingLibrary.getCurrentBatteryLevel());
    }
// return s;
}
Also used : Sample(edu.berkeley.cs.amplab.carat.thrift.Sample)

Example 2 with Sample

use of edu.berkeley.cs.amplab.carat.thrift.Sample in project carat by amplab.

the class SamplerService method takeSampleIfBatteryLevelChanged.

/**
     * Some phones receive the batteryChanged very very often. We are interested 
     * only in changes of the battery level
     * @param intent  The parent intent (the one passed from the Sampler)
	 *				  (with one extra field set, called 'distance')
	 *				  This intent should be the intent which is passed by the Android system to your 
	 *                broadcast receiver (which is registered with the BATTERY_CHANGED action).
	 *                In our case, this broadcast receiver is 'Sampler'.                 
     * @param context
     */
private void takeSampleIfBatteryLevelChanged(Intent intent, Context context) {
    distance = intent.getDoubleExtra("distance", 0);
    // Make sure our new sample doesn't have a zero value as its current battery level
    if (SamplingLibrary.getCurrentBatteryLevel() > 0) {
        CaratSampleDB sampleDB = CaratSampleDB.getInstance(context);
        Sample lastSample = sampleDB.getLastSample(context);
        if (lastSample != null) {
            SamplingLibrary.setLastBatteryLevel(lastSample.getBatteryLevel());
        } else if (SamplingLibrary.getLastBatteryLevel(context) == 0) {
            Log.i(TAG, "The last sample is null (all samples have been uploaded and deleted " + "from the local DB) , and the last battery level is not set yet " + "(the first ever sample). About to take a new sample. " + "currentBatteryLevel=" + SamplingLibrary.getCurrentBatteryLevel());
            // before taking the first sample in a batch, first record the battery level
            SamplingLibrary.setLastBatteryLevel(SamplingLibrary.getCurrentBatteryLevel());
            // take a sample and store it in the database
            this.getSample(context, intent, lastSample, sampleDB);
            notify(context);
        }
        /*
			 * Read the battery levels again, they are now changed. We just
			 * changed the last battery level (in the previous block of code).
			 * The current battery level might also have been changed while the
			 * device has been taking a sample.
			 */
        boolean batteryLevelChanged = SamplingLibrary.getLastBatteryLevel(context) != SamplingLibrary.getCurrentBatteryLevel();
        if (batteryLevelChanged) {
            /* among all occurrence of the event BATTERY_CHANGED, only take a sample 
				 * whenever a battery PERCENTAGE CHANGE happens 
				 * (BATTERY_CHANGED happens whenever the battery temperature or voltage of other parameters change)
				 */
            Log.i(TAG, "The battery percentage changed. About to take a new sample " + "(currentBatteryLevel=" + SamplingLibrary.getCurrentBatteryLevel() + ", lastBatteryLevel=" + SamplingLibrary.getLastBatteryLevel(context) + ")");
            // take a sample and store it in the database
            this.getSample(context, intent, lastSample, sampleDB);
            notify(context);
        } else {
            Log.d(TAG, "NO battery percentage change. currentBatteryLevel=" + SamplingLibrary.getCurrentBatteryLevel());
        }
    } else {
        Log.d(TAG, "current battery level = 0");
    }
}
Also used : Sample(edu.berkeley.cs.amplab.carat.thrift.Sample) CaratSampleDB(edu.berkeley.cs.amplab.carat.android.storage.CaratSampleDB)

Example 3 with Sample

use of edu.berkeley.cs.amplab.carat.thrift.Sample in project carat by amplab.

the class SamplingLibrary method getSample.

public static Sample getSample(Context context, Intent intent, String lastBatteryState) {
    final String TAG = "SamplingLibrary.getSample";
    Log.d(TAG, "getSample() was invoked.");
    String action = intent.getAction();
    Log.d(TAG, "action = " + action);
    // Construct sample and return it in the end
    Sample mySample = new Sample();
    SharedPreferences p = PreferenceManager.getDefaultSharedPreferences(context);
    String uuId = p.getString(CaratApplication.getRegisteredUuid(), null);
    mySample.setUuId(uuId);
    mySample.setTriggeredBy(action);
    // required always
    long now = System.currentTimeMillis();
    mySample.setTimestamp(now / 1000.0);
    // Record first data point for CPU usage
    long[] idleAndCpu1 = readUsagePoint();
    // If the sampler is running because of the SCREEN_ON or SCREEN_OFF
    // event/action,
    // we want to get the info of all installed apps/packages, not only
    // those running.
    // This is because we need the traffic info of all apps, some might not
    // be running when
    // those events (screen on / screen off) occur
    // TODO: let's comment out these lines for debugging purpose
    // if (action.equals(Intent.ACTION_SCREEN_ON) ||
    // action.equals(Intent.ACTION_SCREEN_OFF)) {
    // Log.d(TAG,
    // "the action has been Intent.ACTION_SCREEN_ON or SCREEN_OFF. Taking sample of ALL INSTALLED packages (rather than running processes)");
    // Map<String, ProcessInfo> installedPackages =
    // getInstalledPackages(context, false);
    // List<ProcessInfo> processes = new ArrayList<ProcessInfo>();
    // processes.addAll(installedPackages.values());
    // } else {
    // Log.d(TAG,
    // "the action has NOT been Intent.ACTION_SCREEN_ON or SCREEN_OFF. Taking sample of running processes.");
    List<ProcessInfo> processes = getRunningProcessInfoForSample(context);
    mySample.setPiList(processes);
    // }
    int screenBrightness = SamplingLibrary.getScreenBrightness(context);
    mySample.setScreenBrightness(screenBrightness);
    boolean autoScreenBrightness = SamplingLibrary.isAutoBrightness(context);
    if (autoScreenBrightness)
        // Auto
        mySample.setScreenBrightness(-1);
    // boolean gpsEnabled = SamplingLibrary.getGpsEnabled(context);
    // Location providers
    List<String> enabledLocationProviders = SamplingLibrary.getEnabledLocationProviders(context);
    mySample.setLocationProviders(enabledLocationProviders);
    // TODO: not in Sample yet
    // int maxNumSatellite = SamplingLibrary.getMaxNumSatellite(context);
    String network = SamplingLibrary.getNetworkStatus(context);
    String networkType = SamplingLibrary.getNetworkType(context);
    String mobileNetworkType = SamplingLibrary.getMobileNetworkType(context);
    // Required in new Carat protocol
    if (network.equals(NETWORKSTATUS_CONNECTED)) {
        if (networkType.equals("WIFI"))
            mySample.setNetworkStatus(networkType);
        else
            mySample.setNetworkStatus(mobileNetworkType);
    } else
        mySample.setNetworkStatus(network);
    // String ns = mySample.getNetworkStatus();
    // Log.d(STAG, "Set networkStatus="+ns);
    // Network details
    NetworkDetails nd = new NetworkDetails();
    // Network type
    nd.setNetworkType(networkType);
    nd.setMobileNetworkType(mobileNetworkType);
    boolean roamStatus = SamplingLibrary.getRoamingStatus(context);
    nd.setRoamingEnabled(roamStatus);
    String dataState = SamplingLibrary.getDataState(context);
    nd.setMobileDataStatus(dataState);
    String dataActivity = SamplingLibrary.getDataActivity(context);
    nd.setMobileDataActivity(dataActivity);
    // Wifi stuff
    String wifiState = SamplingLibrary.getWifiState(context);
    nd.setWifiStatus(wifiState);
    int wifiSignalStrength = SamplingLibrary.getWifiSignalStrength(context);
    nd.setWifiSignalStrength(wifiSignalStrength);
    int wifiLinkSpeed = SamplingLibrary.getWifiLinkSpeed(context);
    nd.setWifiLinkSpeed(wifiLinkSpeed);
    // Add NetworkDetails substruct to Sample
    mySample.setNetworkDetails(nd);
    /* Calling Information */
    // List<String> callInfo;
    // callInfo=SamplingLibrary.getCallInfo(context);
    /* Total call time */
    // long totalCallTime=0;
    // totalCallTime=SamplingLibrary.getTotalCallDur(context);
    /*
		 * long[] incomingOutgoingIdle = getCalltimesSinceBoot(context);
		 * Log.d(STAG, "Call time since boot: Incoming=" +
		 * incomingOutgoingIdle[0] + " Outgoing=" + incomingOutgoingIdle[1] +
		 * " idle=" + incomingOutgoingIdle[2]);
		 * 
		 * // Summary Call info CallInfo ci = new CallInfo(); String callState =
		 * SamplingLibrary.getCallState(context); ci.setCallStatus(callState);
		 * ci.setIncomingCallTime(incomingOutgoingIdle[0]);
		 * ci.setOutgoingCallTime(incomingOutgoingIdle[1]);
		 * ci.setNonCallTime(incomingOutgoingIdle[2]);
		 * 
		 * mySample.setCallInfo(ci);
		 */
    // Bundle b = intent.getExtras();
    int health = intent.getIntExtra(BatteryManager.EXTRA_HEALTH, 0);
    int status = intent.getIntExtra(BatteryManager.EXTRA_STATUS, 0);
    // This is really an int.
    // FIXED: Not used yet, Sample needs more fields
    int plugged = intent.getIntExtra(BatteryManager.EXTRA_PLUGGED, 0);
    String batteryTechnology = intent.getExtras().getString(BatteryManager.EXTRA_TECHNOLOGY);
    // FIXED: Not used yet, Sample needs more fields
    String batteryHealth = "Unknown";
    String batteryStatus = "Unknown";
    switch(health) {
        case BatteryManager.BATTERY_HEALTH_DEAD:
            batteryHealth = "Dead";
            break;
        case BatteryManager.BATTERY_HEALTH_GOOD:
            batteryHealth = "Good";
            break;
        case BatteryManager.BATTERY_HEALTH_OVER_VOLTAGE:
            batteryHealth = "Over voltage";
            break;
        case BatteryManager.BATTERY_HEALTH_OVERHEAT:
            batteryHealth = "Overheat";
            break;
        case BatteryManager.BATTERY_HEALTH_UNKNOWN:
            batteryHealth = "Unknown";
            break;
        case BatteryManager.BATTERY_HEALTH_UNSPECIFIED_FAILURE:
            batteryHealth = "Unspecified failure";
            break;
    }
    switch(status) {
        case BatteryManager.BATTERY_STATUS_CHARGING:
            batteryStatus = "Charging";
            break;
        case BatteryManager.BATTERY_STATUS_DISCHARGING:
            batteryStatus = "Discharging";
            break;
        case BatteryManager.BATTERY_STATUS_FULL:
            batteryStatus = "Full";
            break;
        case BatteryManager.BATTERY_STATUS_NOT_CHARGING:
            batteryStatus = "Not charging";
            break;
        case BatteryManager.BATTERY_STATUS_UNKNOWN:
            batteryStatus = "Unknown";
            break;
        default:
            batteryStatus = lastBatteryState != null ? lastBatteryState : "Unknown";
    }
    // FIXED: Not used yet, Sample needs more fields
    String batteryCharger = "unplugged";
    switch(plugged) {
        case BatteryManager.BATTERY_PLUGGED_AC:
            batteryCharger = "ac";
            break;
        case BatteryManager.BATTERY_PLUGGED_USB:
            batteryCharger = "usb";
            break;
    }
    BatteryDetails bd = new BatteryDetails();
    // otherInfo.setCPUIdleTime(totalIdleTime);
    // IMPORTANT: All of the battery details fields were never set (=always
    // zero), like the last battery level.
    // Now all must have been fixed.
    // current battery temperature in degrees Centigrade (the unit of the
    // temperature value
    // (returned by BatteryManager) is not Centigrade, it should be divided
    // by 10)
    int temperature = intent.getIntExtra(BatteryManager.EXTRA_TEMPERATURE, 0) / 10;
    bd.setBatteryTemperature(temperature);
    // otherInfo.setBatteryTemperature(temperature);
    // current battery voltage in VOLTS (the unit of the returned value by
    // BatteryManager is millivolts)
    double voltage = intent.getIntExtra(BatteryManager.EXTRA_VOLTAGE, 0) / 1000;
    bd.setBatteryVoltage(voltage);
    // otherInfo.setBatteryVoltage(voltage);
    bd.setBatteryTechnology(batteryTechnology);
    bd.setBatteryCharger(batteryCharger);
    bd.setBatteryHealth(batteryHealth);
    mySample.setBatteryDetails(bd);
    mySample.setBatteryLevel(currentBatteryLevel);
    mySample.setBatteryState(batteryStatus);
    int[] usedFreeActiveInactive = SamplingLibrary.readMeminfo();
    if (usedFreeActiveInactive != null && usedFreeActiveInactive.length == 4) {
        mySample.setMemoryUser(usedFreeActiveInactive[0]);
        mySample.setMemoryFree(usedFreeActiveInactive[1]);
        mySample.setMemoryActive(usedFreeActiveInactive[2]);
        mySample.setMemoryInactive(usedFreeActiveInactive[3]);
    }
    // TODO: Memory Wired should have memory that is "unevictable", that
    // will always be used even when all apps are killed
    // Log.d(STAG, "serial=" + getBuildSerial());
    // Record second data point for cpu/idle time
    now = System.currentTimeMillis();
    long[] idleAndCpu2 = readUsagePoint();
    CpuStatus cs = new CpuStatus();
    cs.setCpuUsage(getUsage(idleAndCpu1, idleAndCpu2));
    cs.setUptime(getUptime());
    mySample.setCpuStatus(cs);
    mySample.setDeveloperMode(isDeveloperModeOn(context));
    mySample.setUnknownSources(allowUnknownSources(context));
    mySample.setScreenOn(isScreenOn(context));
    mySample.setTimeZone(getTimeZone(context));
    // printAverageFeaturePower(context);
    // If there are extra fields, include them into the sample.
    List<Feature> extras = getExtras(context);
    if (extras != null && extras.size() > 0)
        mySample.setExtra(extras);
    return mySample;
}
Also used : CpuStatus(edu.berkeley.cs.amplab.carat.thrift.CpuStatus) SharedPreferences(android.content.SharedPreferences) Sample(edu.berkeley.cs.amplab.carat.thrift.Sample) NetworkDetails(edu.berkeley.cs.amplab.carat.thrift.NetworkDetails) RunningAppProcessInfo(android.app.ActivityManager.RunningAppProcessInfo) ProcessInfo(edu.berkeley.cs.amplab.carat.thrift.ProcessInfo) Feature(edu.berkeley.cs.amplab.carat.thrift.Feature) BatteryDetails(edu.berkeley.cs.amplab.carat.thrift.BatteryDetails)

Example 4 with Sample

use of edu.berkeley.cs.amplab.carat.thrift.Sample in project carat by amplab.

the class SampleSender method sendSamples.

public static void sendSamples(CaratApplication app) {
    synchronized (sendLock) {
        Context c = app.getApplicationContext();
        String networkStatus = SamplingLibrary.getNetworkStatus(c);
        String networkType = SamplingLibrary.getNetworkType(c);
        final SharedPreferences p = PreferenceManager.getDefaultSharedPreferences(c);
        final boolean useWifiOnly = p.getBoolean(Constants.WIFI_ONLY_PREFERENCE_KEY, false);
        Log.i("wifi-preference-SampleSender", String.valueOf(useWifiOnly));
        boolean connected = (!useWifiOnly && networkStatus == SamplingLibrary.NETWORKSTATUS_CONNECTED) || networkType.equals("WIFI");
        if (connected) {
            CaratSampleDB db = CaratSampleDB.getInstance(c);
            int samples = db.countSamples();
            /* Click Tracking: Track sample sending. */
            String uuId = p.getString(CaratApplication.getRegisteredUuid(), "UNKNOWN");
            HashMap<String, String> options = new HashMap<String, String>();
            options.put("count", samples + "");
            ClickTracking.track(uuId, "sendingsamples", options, c);
            /* End Click Tracking: Track sample sending. */
            int successSum = 0;
            for (int batches = 0; batches < Constants.COMMS_MAX_BATCHES && batches < samples / Constants.COMMS_MAX_UPLOAD_BATCH + 1; batches++) {
                SortedMap<Long, Sample> map = CaratSampleDB.getInstance(c).queryOldestSamples(Constants.COMMS_MAX_UPLOAD_BATCH);
                if (map.size() > 0) {
                    int progress = (int) (successSum * 1.0 / samples * 100.0);
                    CaratApplication.setActionProgress(progress, successSum + "/" + samples + " " + app.getString(R.string.samplesreported), false);
                    if (app.commManager != null) {
                        int tries = 0;
                        while (tries < 2) {
                            try {
                                int success = app.commManager.uploadSamples(map.values());
                                tries = 2;
                                // FlurryAgent.logEvent("UploadSamples");
                                Log.d(TAG, "Uploaded " + success + " samples out of " + map.size());
                                if (success > 0)
                                    CaratApplication.storage.samplesReported(success);
                                Sample last = map.get(map.lastKey());
                                /*
									 * converting (to human readable date-time format) 
									 * the "timestamp" of the last sample (which is
									 * uploaded now, and should be deleted along the other 
									 * uploaded samples). The "timestamp" is computed this way:
									 * CurrentTimeMillis / 1000 
									 * (see getSample() in SamplingLibrary)
									 */
                                // in currentTimeMillis
                                long lastSampleTime = (long) last.getTimestamp() * 1000;
                                SimpleDateFormat sdf = new SimpleDateFormat("MMM dd,yyyy HH:mm");
                                Date resultdate = new Date(lastSampleTime);
                                Log.d(TAG, "Deleting " + success + " samples older than " + sdf.format(resultdate));
                                /*
                                     * Log.i(TAG, "Sent samples:"); for (Sample k:
                                     * map.values()){ Log.i(TAG, k.getTimestamp() +
                                     * " " + k.getBatteryLevel()); }
                                     */
                                SortedSet<Long> uploaded = new TreeSet<Long>();
                                int i = 0;
                                for (Long s : map.keySet()) {
                                    if (i < success)
                                        uploaded.add(s);
                                    i += 1;
                                }
                                int deleted = CaratSampleDB.getInstance(c).deleteSamples(uploaded);
                                // Log.d(TAG, "Deleted " + deleted + " samples.");
                                successSum += success;
                            } catch (Throwable th) {
                                // Any sort of malformed response, too short
                                // string, etc...
                                Log.w(TAG, "Failed to refresh reports: " + th + (tries < 1 ? "Trying again now" : TRY_AGAIN), th);
                                tries++;
                            }
                        }
                    } else {
                        Log.w(TAG, "CommunicationManager is not ready yet." + TRY_AGAIN);
                    }
                } else {
                    Log.w(TAG, "No samples to send." + TRY_AGAIN);
                }
            }
            /* Click Tracking: Track sample sending. */
            options.put("count", successSum + "");
            ClickTracking.track(uuId, "sentsamples", options, c);
        /* End Click Tracking: Track sample sending. */
        }
    /* else if (networkStatus
                    .equals(SamplingLibrary.NETWORKSTATUS_CONNECTING)) {
                Log.w(TAG, "Network status: " + networkStatus
                        + ", trying again in 10s.");
                connecting = true;
            } else {
                Log.w(TAG, "Network status: " + networkStatus + TRY_AGAIN);
                connecting = false;
            }
            if (connecting) {
                // wait for wifi to come up
                try {
                    Thread.sleep(CaratApplication.COMMS_WIFI_WAIT);
                } catch (InterruptedException e1) {
                    // ignore
                }
                connecting = false;
            } else {
                try {
                    Thread.sleep(CaratApplication.COMMS_INTERVAL);
                } catch (InterruptedException e) {
                    // wait for wifi to come up
                    try {
                        Thread.sleep(CaratApplication.COMMS_WIFI_WAIT);
                    } catch (InterruptedException e1) {
                        // ignore
                    }
                }
            }*/
    }
}
Also used : Context(android.content.Context) SharedPreferences(android.content.SharedPreferences) HashMap(java.util.HashMap) Sample(edu.berkeley.cs.amplab.carat.thrift.Sample) CaratSampleDB(edu.berkeley.cs.amplab.carat.android.storage.CaratSampleDB) Date(java.util.Date) TreeSet(java.util.TreeSet) SimpleDateFormat(java.text.SimpleDateFormat)

Example 5 with Sample

use of edu.berkeley.cs.amplab.carat.thrift.Sample in project carat by amplab.

the class CaratSampleDB method queryLastSample.

private Sample queryLastSample() {
    String[] columns = mColumnMap.keySet().toArray(new String[mColumnMap.size()]);
    Cursor cursor = query(null, null, columns, null, null, COLUMN_TIMESTAMP + " DESC LIMIT 1");
    if (cursor == null) {
        // There are no results
        return null;
    } else {
        cursor.moveToFirst();
        if (!cursor.isAfterLast()) {
            Sample s = fillSample(cursor);
            cursor.close();
            lastSample = s;
            return s;
        }
        cursor.close();
        return null;
    }
}
Also used : Sample(edu.berkeley.cs.amplab.carat.thrift.Sample) Cursor(android.database.Cursor)

Aggregations

Sample (edu.berkeley.cs.amplab.carat.thrift.Sample)9 Feature (edu.berkeley.cs.amplab.carat.thrift.Feature)3 ProcessInfo (edu.berkeley.cs.amplab.carat.thrift.ProcessInfo)3 HashMap (java.util.HashMap)3 SharedPreferences (android.content.SharedPreferences)2 Cursor (android.database.Cursor)2 CaratSampleDB (edu.berkeley.cs.amplab.carat.android.storage.CaratSampleDB)2 BatteryDetails (edu.berkeley.cs.amplab.carat.thrift.BatteryDetails)2 CpuStatus (edu.berkeley.cs.amplab.carat.thrift.CpuStatus)2 NetworkDetails (edu.berkeley.cs.amplab.carat.thrift.NetworkDetails)2 Sample._Fields (edu.berkeley.cs.amplab.carat.thrift.Sample._Fields)2 FieldMetaData (org.apache.thrift.meta_data.FieldMetaData)2 RunningAppProcessInfo (android.app.ActivityManager.RunningAppProcessInfo)1 Context (android.content.Context)1 CaratService (edu.berkeley.cs.amplab.carat.thrift.CaratService)1 ByteArrayInputStream (java.io.ByteArrayInputStream)1 IOException (java.io.IOException)1 ObjectInputStream (java.io.ObjectInputStream)1 StreamCorruptedException (java.io.StreamCorruptedException)1 SimpleDateFormat (java.text.SimpleDateFormat)1