Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit f27f036d authored by Darin Petkov's avatar Darin Petkov
Browse files

Update metrics_daemon to use base/time.h instead of time_t directly.

Also, guard against time jumps in the active daily use metric collection.

BUG=none
TEST=unit tests; gmerge'd on the target device and inspected the logs.

Review URL: http://codereview.chromium.org/2576005
parent f1172ff6
Loading
Loading
Loading
Loading
+30 −17
Original line number Diff line number Diff line
@@ -10,6 +10,10 @@
#include <base/eintr_wrapper.h>
#include <base/logging.h>

using base::Time;
using base::TimeDelta;
using base::TimeTicks;

#define SAFE_MESSAGE(e) (e.message ? e.message : "unknown error")
#define DBUS_IFACE_CONNMAN_MANAGER "org.moblin.connman.Manager"
#define DBUS_IFACE_POWER_MANAGER "org.chromium.Power.Manager"
@@ -25,7 +29,6 @@ static const int kSecondsPerMinute = 60;
static const int kMinutesPerHour = 60;
static const int kHoursPerDay = 24;
static const int kMinutesPerDay = kHoursPerDay * kMinutesPerHour;
static const int kSecondsPerDay = kMinutesPerDay * kSecondsPerMinute;

// The daily use monitor is scheduled to a 1-minute interval after
// initial user activity and then it's exponentially backed off to
@@ -152,8 +155,9 @@ void MetricsDaemon::Loop() {
DBusHandlerResult MetricsDaemon::MessageFilter(DBusConnection* connection,
                                               DBusMessage* message,
                                               void* user_data) {
  time_t now = time(NULL);
  DLOG(INFO) << "message intercepted @ " << now;
  Time now = Time::Now();
  TimeTicks ticks = TimeTicks::Now();
  DLOG(INFO) << "message intercepted @ " << now.ToInternalValue();

  int message_type = dbus_message_get_type(message);
  if (message_type != DBUS_MESSAGE_TYPE_SIGNAL) {
@@ -175,7 +179,7 @@ DBusHandlerResult MetricsDaemon::MessageFilter(DBusConnection* connection,

    char *state_name;
    dbus_message_iter_get_basic(&iter, &state_name);
    daemon->NetStateChanged(state_name, now);
    daemon->NetStateChanged(state_name, ticks);
  } else if (strcmp(interface, DBUS_IFACE_POWER_MANAGER) == 0) {
    CHECK(strcmp(dbus_message_get_member(message),
                 "PowerStateChanged") == 0);
@@ -205,7 +209,7 @@ DBusHandlerResult MetricsDaemon::MessageFilter(DBusConnection* connection,
  return DBUS_HANDLER_RESULT_HANDLED;
}

void MetricsDaemon::NetStateChanged(const char* state_name, time_t now) {
void MetricsDaemon::NetStateChanged(const char* state_name, TimeTicks ticks) {
  DLOG(INFO) << "network state: " << state_name;

  NetworkState state = LookupNetworkState(state_name);
@@ -219,7 +223,8 @@ void MetricsDaemon::NetStateChanged(const char* state_name, time_t now) {
  if (state != kNetworkStateOnline &&
      network_state_ == kNetworkStateOnline &&
      power_state_ != kPowerStateMem) {
    int online_time = static_cast<int>(now - network_state_last_);
    TimeDelta since_online = ticks - network_state_last_;
    int online_time = static_cast<int>(since_online.InSeconds());
    SendMetric(kMetricTimeToNetworkDropName, online_time,
               kMetricTimeToNetworkDropMin,
               kMetricTimeToNetworkDropMax,
@@ -227,7 +232,7 @@ void MetricsDaemon::NetStateChanged(const char* state_name, time_t now) {
  }

  network_state_ = state;
  network_state_last_ = now;
  network_state_last_ = ticks;
}

MetricsDaemon::NetworkState
@@ -241,7 +246,7 @@ MetricsDaemon::LookupNetworkState(const char* state_name) {
  return kUnknownNetworkState;
}

void MetricsDaemon::PowerStateChanged(const char* state_name, time_t now) {
void MetricsDaemon::PowerStateChanged(const char* state_name, Time now) {
  DLOG(INFO) << "power state: " << state_name;
  power_state_ = LookupPowerState(state_name);

@@ -260,8 +265,7 @@ MetricsDaemon::LookupPowerState(const char* state_name) {
  return kUnknownPowerState;
}

void MetricsDaemon::ScreenSaverStateChanged(const char* state_name,
                                            time_t now) {
void MetricsDaemon::ScreenSaverStateChanged(const char* state_name, Time now) {
  DLOG(INFO) << "screen-saver state: " << state_name;
  screensaver_state_ = LookupScreenSaverState(state_name);
  SetUserActiveState(screensaver_state_ == kScreenSaverStateUnlocked, now);
@@ -278,8 +282,7 @@ MetricsDaemon::LookupScreenSaverState(const char* state_name) {
  return kUnknownScreenSaverState;
}

void MetricsDaemon::SessionStateChanged(const char* state_name,
                                        time_t now) {
void MetricsDaemon::SessionStateChanged(const char* state_name, Time now) {
  DLOG(INFO) << "user session state: " << state_name;
  session_state_ = LookupSessionState(state_name);
  SetUserActiveState(session_state_ == kSessionStateStarted, now);
@@ -296,13 +299,23 @@ MetricsDaemon::LookupSessionState(const char* state_name) {
  return kUnknownSessionState;
}

void MetricsDaemon::SetUserActiveState(bool active, time_t now) {
void MetricsDaemon::SetUserActiveState(bool active, Time now) {
  DLOG(INFO) << "user: " << (active ? "active" : "inactive");

  // Calculates the seconds of active use since the last update and
  // the day since Epoch, and logs the usage data.
  int seconds = user_active_ ? (now - user_active_last_) : 0;
  int day = now / kSecondsPerDay;
  // the day since Epoch, and logs the usage data.  Guards against the
  // time jumping back and forth due to the user changing it by
  // discarding the new use time.
  int seconds = 0;
  if (user_active_ && now > user_active_last_) {
    TimeDelta since_active = now - user_active_last_;
    if (since_active < TimeDelta::FromSeconds(
            kUseMonitorIntervalMax + kSecondsPerMinute)) {
      seconds = static_cast<int>(since_active.InSeconds());
    }
  }
  TimeDelta since_epoch = now - Time();
  int day = since_epoch.InDays();
  LogDailyUseRecord(day, seconds);

  // Schedules a use monitor on inactive->active transitions and
@@ -388,7 +401,7 @@ gboolean MetricsDaemon::UseMonitorStatic(gpointer data) {
}

bool MetricsDaemon::UseMonitor() {
  SetUserActiveState(user_active_, time(NULL));
  SetUserActiveState(user_active_, Time::Now());

  // If a new monitor source/instance is scheduled, returns false to
  // tell GLib to destroy this monitor source/instance. Returns true
+19 −13
Original line number Diff line number Diff line
@@ -7,11 +7,11 @@

#include <dbus/dbus.h>
#include <glib.h>
#include <time.h>

#include "metrics_library.h"

#include <gtest/gtest_prod.h>  // for FRIEND_TEST
#include <base/time.h>

class MetricsDaemon {

@@ -19,12 +19,10 @@ class MetricsDaemon {
  MetricsDaemon()
      : daily_use_record_file_(NULL),
        network_state_(kUnknownNetworkState),
        network_state_last_(0),
        power_state_(kUnknownPowerState),
        screensaver_state_(kUnknownScreenSaverState),
        session_state_(kUnknownSessionState),
        user_active_(false),
        user_active_last_(0),
        daily_use_day_last_(0),
        usemon_interval_(0),
        usemon_source_(NULL) {}
@@ -56,6 +54,7 @@ class MetricsDaemon {
  FRIEND_TEST(MetricsDaemonTest, SessionStateChanged);
  FRIEND_TEST(MetricsDaemonTest, SetUserActiveStateSendOnLogin);
  FRIEND_TEST(MetricsDaemonTest, SetUserActiveStateSendOnMonitor);
  FRIEND_TEST(MetricsDaemonTest, SetUserActiveStateTimeJump);

  // The network states (see network_states.h).
  enum NetworkState {
@@ -131,25 +130,25 @@ class MetricsDaemon {
                                         void* user_data);

  // Processes network state change.
  void NetStateChanged(const char* state_name, time_t now);
  void NetStateChanged(const char* state_name, base::TimeTicks ticks);

  // Given the state name, returns the state id.
  NetworkState LookupNetworkState(const char* state_name);

  // Processes power state change.
  void PowerStateChanged(const char* state_name, time_t now);
  void PowerStateChanged(const char* state_name, base::Time now);

  // Given the state name, returns the state id.
  PowerState LookupPowerState(const char* state_name);

  // Processes screen-saver state change.
  void ScreenSaverStateChanged(const char* state_name, time_t now);
  void ScreenSaverStateChanged(const char* state_name, base::Time now);

  // Given the state name, returns the state id.
  ScreenSaverState LookupScreenSaverState(const char* state_name);

  // Processes user session state change.
  void SessionStateChanged(const char* state_name, time_t now);
  void SessionStateChanged(const char* state_name, base::Time now);

  // Given the state name, returns the state id.
  SessionState LookupSessionState(const char* state_name);
@@ -158,7 +157,10 @@ class MetricsDaemon {
  // since the last update. If the user has just become active,
  // reschedule the daily use monitor for more frequent updates --
  // this is followed by an exponential back-off (see UseMonitor).
  void SetUserActiveState(bool active, time_t now);
  // While in active use, this method should be called at intervals no
  // longer than kUseMonitorIntervalMax otherwise new use time will be
  // discarded.
  void SetUserActiveState(bool active, base::Time now);

  // Updates the daily usage file, if necessary, by adding |seconds|
  // of active use to the |day| since Epoch. If there's usage data for
@@ -205,8 +207,10 @@ class MetricsDaemon {
  // Current network state.
  NetworkState network_state_;

  // Timestamps last network state update.
  time_t network_state_last_;
  // Timestamps last network state update.  This timestamp is used to
  // sample the time from the network going online to going offline so
  // TimeTicks ensures a monotonically increasing TimeDelta.
  base::TimeTicks network_state_last_;

  // Current power state.
  PowerState power_state_;
@@ -221,10 +225,12 @@ class MetricsDaemon {
  // started, screen is not locked.
  bool user_active_;

  // Timestamps last user active update.
  time_t user_active_last_;
  // Timestamps last user active update.  Active use time is
  // aggregated each day before sending to UMA so using time since the
  // epoch as the timestamp.
  base::Time user_active_last_;

  // Last stored daily use day (since epoch).
  // Last stored daily use day (since the epoch).
  int daily_use_day_last_;

  // Sleep period until the next daily usage aggregation performed by
+134 −110

File changed.

Preview size limit exceeded, changes collapsed.