Usage Statistics (usagestats) Log Documentation

Introduction

The Usage Statistics service (usagestats) tracks detailed application usage patterns, providing forensic investigators with critical timeline data about user activities. This service records when apps are launched, how long they're used, and user interaction patterns.

Prerequisites

  • Android device with USB debugging enabled
  • ADB (Android Debug Bridge) installed
  • Android 5.0 (API 21) or higher
  • Usage access permission enabled on device

Step 1: Enable Usage Access Permission

Before extracting usage statistics, ensure the permission is granted:

bash
# Check if usage stats permission is granted
adb shell dumpsys usagestats | head -20

# If you see "Usage stats access denied", enable it:
# On device: Settings → Security → Usage access → Enable for "Shell"
# Or via ADB (requires user interaction):

adb shell am start -a android.settings.USAGE_ACCESS_SETTINGS

Step 2: Basic Usage Statistics Extraction

Create your working directory and extract usage data:

bash
# Create evidence directory
mkdir usagestats_evidence
cd usagestats_evidence

# Extract complete usage statistics
adb shell dumpsys usagestats > usagestats_full.txt

# Extract specific time periods
adb shell dumpsys usagestats --hours 24 > usagestats_24hours.txt
adb shell dumpsys usagestats --days 7 > usagestats_7days.txt

# Extract different aggregation types
adb shell dumpsys usagestats daily > usagestats_daily.txt
adb shell dumpsys usagestats weekly > usagestats_weekly.txt
adb shell dumpsys usagestats monthly > usagestats_monthly.txt

adb shell dumpsys usagestats yearly > usagestats_yearly.txt

Step 3: Understanding the Output Structure

Open usagestats_full.txt and observe the structure:

DUMP OF SERVICE usagestats:
userId=0

In-memory daily stats
time range: 1705276800000 - 1705363200000 (2024-01-15 00:00 - 2024-01-16 00:00)

packages:  
  package=com.android.chrome userId=0  
    totalTimeUsed=3456000        \# 57.6 minutes  
    lastTimeUsed=1705359842000    \# 2024-01-15 23:04:02  
    totalTimeForeground=3456000  
    lastTimeForeground=1705359842000  
    appLaunchCount=12

  package=com.whatsapp userId=0  
    totalTimeUsed=8765000        \# 146 minutes  
    lastTimeUsed=1705361245000    \# 2024-01-15 23:27:25  
    totalTimeForeground=8765000  
    lastTimeForeground=1705361245000  
    appLaunchCount=45

events:  
  time=1705277400000 type=ACTIVITY\_RESUMED package=com.android.launcher3 class=com.android.launcher3.Launcher  
  time=1705277415000 type=ACTIVITY\_PAUSED package=com.android.launcher3

  time=1705277415000 type=ACTIVITY\_RESUMED package=com.whatsapp class=com.whatsapp.HomeActivity

Step 4: First Analysis Exercise

Let's identify the most used apps today:

bash
# Extract today's usage and sort by time
grep -A3 "totalTimeUsed=" usagestats_24hours.txt | \
grep -E "package=|totalTimeUsed=" | \
paste - - | \
sed 's/.*package=//' | \
sed 's/ userId.*totalTimeUsed=/ /' | \
sort -k2 -nr | \
head -10 | \
awk '{
hours \= int($2/3600000)
minutes \= int(($2%3600000)/60000)
printf "%-40s %2dh %2dm\n", $1, hours, minutes

}'

Understanding Key Components

  1. Package Statistics
  2. totalTimeUsed - Total milliseconds in foreground
  3. lastTimeUsed - Last foreground timestamp
  4. appLaunchCount - Number of times launched
  5. totalTimeForeground - Active usage time

Event Types
1 \= ACTIVITY_RESUMED # App came to foreground
2 \= ACTIVITY_PAUSED # App went to background
5 \= CONFIGURATION_CHANGE # Screen rotation, etc.
7 \= USER_INTERACTION # User touched screen
8 \= SHORTCUT_INVOCATION # Shortcut used
11 \= STANDBY_BUCKET_CHANGED # App standby state changed
15 \= SCREEN_INTERACTIVE # Screen turned on
16 \= SCREEN_NON_INTERACTIVE # Screen turned off

  1. 23 \= ACTIVITY_STOPPED # App stopped
  2. Time Aggregations
  3. Daily: Last 7 days
  4. Weekly: Last 4 weeks
  5. Monthly: Last 6 months
  6. Yearly: Last 2 years

Working with Usage Statistics Logs

How to Extract Specific Timeframes

Extract Custom Date Range

bash
# Function to convert date to milliseconds
date_to_ms() {
date -d "$1" +%s000
}

# Extract usage between specific dates
START_DATE=$(date_to_ms "2024-01-10 00:00:00")
END_DATE=$(date_to_ms "2024-01-15 23:59:59")

# Filter events within date range
awk -v start="$START_DATE" -v end="$END_DATE" '
/time=/ {
time \= $0
gsub(/.*time=/, "", time)
gsub(/ .*/, "", time)
if (time >= start && time \<= end) {
print strftime("%Y-%m-%d %H:%M:%S", time/1000), $0
}
}

' usagestats_full.txt > filtered_timerange.txt

Extract Hourly Usage Patterns

bash
# Create hourly usage distribution
grep "type=ACTIVITY_RESUMED" usagestats_full.txt | \
awk '{
match($0, /time=([0-9]+)/, arr)
hour \= strftime("%H", arr[1]/1000)
hours[hour]++
}
END {
for (h=0; h\<24; h++) {
printf "%02d:00 - %02d:59: %d app launches\n", h, h, hours[sprintf("%02d", h)]
}

}' | sort > hourly_usage_pattern.txt

How to Filter for Specific Events

Track Specific App Usage

bash
# Monitor WhatsApp usage patterns
TARGET_APP="com.whatsapp"

# Extract all events for target app
grep "$TARGET_APP" usagestats_full.txt > ${TARGET_APP}_events.txt

# Create usage timeline
awk '/type=ACTIVITY_RESUMED/ {
match($0, /time=([0-9]+)/, start_time)
}
/type=ACTIVITY_PAUSED/ {
match($0, /time=([0-9]+)/, end_time)
if (start_time[1]) {
duration \= (end_time[1] - start_time[1]) / 1000
printf "%s - %s (%d seconds)\n",
strftime("%Y-%m-%d %H:%M:%S", start_time[1]/1000),
strftime("%H:%M:%S", end_time[1]/1000),
duration
delete start_time
}

}' ${TARGET_APP}_events.txt > ${TARGET_APP}_sessions.txt

Identify App Launch Sequences

bash
# Extract app launch sequences (which apps are opened after each other)
awk '
/type=ACTIVITY_RESUMED/ {
match($0, /time=([0-9]+)/, t)
match($0, /package=([^ ]+)/, p)
if (last_pkg && (t[1] - last_time) \< 60000) { # Within 1 minute
sequences[last_pkg " -> " p[1]]++
}
last_pkg \= p[1]
last_time \= t[1]
}
END {
print "Common App Sequences (within 1 minute):"
for (seq in sequences) {
if (sequences[seq] > 2) {
printf "%3d times: %s\n", sequences[seq], seq
}
}
}

' usagestats_full.txt | sort -nr > app_sequences.txt

How to Correlate with Other Logs

Correlate with Screen On/Off Events

bash
# Extract screen events
grep -E "SCREEN_INTERACTIVE|SCREEN_NON_INTERACTIVE" usagestats_full.txt > screen_events.txt

# Combine with app usage
cat screen_events.txt usagestats_full.txt | \
grep -E "SCREEN_|ACTIVITY_RESUMED" | \
sort -k2 -t\= -n | \
awk '
/SCREEN_INTERACTIVE/ {screen="ON"; time=$2; gsub(/.*time=/, "", time); gsub(/ .*/, "", time)}
/SCREEN_NON_INTERACTIVE/ {screen="OFF"; time=$2; gsub(/.*time=/, "", time); gsub(/ .*/, "", time)}
/ACTIVITY_RESUMED/ {
if (screen \== "ON") {
match($0, /package=([^ ]+)/, pkg)
match($0, /time=([0-9]+)/, t)
print strftime("%Y-%m-%d %H:%M:%S", t[1]/1000), "Screen ON - Launched:", pkg[1]
}
}

' > screen_correlation.txt

Cross-Reference with Battery Stats

bash
# Get heavy battery consuming periods
adb shell dumpsys batterystats --charged | \
grep -A10 "Estimated power use" > battery_drain.txt

# Extract usage during battery drain periods
# This helps identify apps causing battery drain
HIGH_DRAIN_START=$(date_to_ms "2024-01-15 14:00:00")
HIGH_DRAIN_END=$(date_to_ms "2024-01-15 16:00:00")

awk -v start="$HIGH_DRAIN_START" -v end="$HIGH_DRAIN_END" '
/package=/ && /totalTimeUsed=/ {
pkg \= $0
gsub(/.*package=/, "", pkg)
gsub(/ .*totalTimeUsed=/, " ", pkg)
gsub(/ .*/, "", pkg)

if ($0 \~ /lastTimeUsed=/) {  
  match($0, /lastTimeUsed=(\[0-9\]+)/, last)  
  if (last\[1\] \>= start && last\[1\] \<= end) {  
    print pkg " active during high battery drain"  
  }  
}

}

' usagestats_full.txt > battery_correlation.txt

How to Identify Anomalies

Detect Unusual Usage Patterns

bash
# Find apps used at unusual hours (2 AM - 5 AM)
awk '
/type=ACTIVITY_RESUMED/ {
match($0, /time=([0-9]+)/, t)
match($0, /package=([^ ]+)/, p)
hour \= strftime("%H", t[1]/1000)
if (hour >= "02" && hour \<= "05") {
unusual[p[1]]++
print strftime("%Y-%m-%d %H:%M:%S", t[1]/1000), p[1]
}
}
END {
print "\nSummary of night usage (2-5 AM):"
for (app in unusual) {
print app ": " unusual[app] " times"
}
}

' usagestats_full.txt > unusual_hours_usage.txt

Identify Hidden App Usage

bash
# Find apps with usage but no launcher activity
# First get apps with usage
grep "package=" usagestats_full.txt | \
grep -v "totalTimeUsed=0" | \
sed 's/.*package=//' | \
sed 's/ .*//' | \
sort -u > used_apps.txt

# Get apps with launcher
adb shell cmd package list packages | \
while read pkg; do
pkg_name=${pkg#package:}
if adb shell dumpsys package $pkg_name | grep -q "android.intent.category.LAUNCHER"; then
echo $pkg_name
fi
done > launcher_apps.txt

# Find apps used but not in launcher

comm -23 used_apps.txt launcher_apps.txt > hidden_active_apps.txt

Usage Statistics Log Structure

Complete Field Definitions

Package Usage Entry Structure

package=[package.name] userId=[user_id]
totalTimeUsed=[milliseconds] # Total foreground time
lastTimeUsed=[timestamp_ms] # Last time in foreground
totalTimeForeground=[milliseconds] # Same as totalTimeUsed
lastTimeForeground=[timestamp_ms] # Same as lastTimeUsed
totalTimeVisible=[milliseconds] # Time visible (Android 10+)
lastTimeVisible=[timestamp_ms] # Last visible time
totalTimeInForeground=[milliseconds] # Legacy field
lastTimeComponentUsed=[timestamp_ms] # Component-level tracking
appLaunchCount=[count] # Number of launches
appStandbyBucket=[bucket_value] # 10=Active, 20=Working, 30=Frequent, 40=Rare
lastJobRunTime=[timestamp_ms] # Last background job

lastSyncTime=[timestamp_ms] # Last sync operation

Event Entry Structure

time=[timestamp_ms] type=[event_type] package=[package.name] class=[component.class] flags=[hex_flags]

Event Types:
1 \= ACTIVITY_RESUMED # Component came to foreground
2 \= ACTIVITY_PAUSED # Component left foreground
3 \= END_OF_DAY # Day boundary crossed
4 \= CONTINUE_PREVIOUS_DAY # Continuation from previous
5 \= CONFIGURATION_CHANGE # Config changed (rotation)
6 \= SYSTEM_INTERACTION # System UI interaction
7 \= USER_INTERACTION # User touched app
8 \= SHORTCUT_INVOCATION # Shortcut launched
9 \= CHOOSER_ACTION # Share/chooser used
10 \= NOTIFICATION_SEEN # Notification viewed
11 \= STANDBY_BUCKET_CHANGED # App standby changed
12 \= NOTIFICATION_INTERRUPTION # Notification appeared
15 \= SCREEN_INTERACTIVE # Screen turned on
16 \= SCREEN_NON_INTERACTIVE # Screen turned off
17 \= KEYGUARD_SHOWN # Lock screen shown
18 \= KEYGUARD_HIDDEN # Device unlocked
23 \= ACTIVITY_STOPPED # Activity fully stopped
26 \= DEVICE_SHUTDOWN # Device shutting down

27 \= DEVICE_STARTUP # Device booted

Configuration Structure

config={
mcc=[mobile_country_code] # e.g., 310 for US
mnc=[mobile_network_code] # e.g., 260 for T-Mobile
locale=[language_region] # e.g., en_US
touchscreen=[type] # 3=finger
keyboard=[type] # 1=nokeys, 2=qwerty
navigation=[type] # 1=nonav, 2=dpad, 3=trackball
orientation=[value] # 1=portrait, 2=landscape
screenLayout=[size_long] # Encoded layout info
colorMode=[wide_hdr] # Color capabilities
uiMode=[type_night] # UI mode settings
screenWidthDp=[width] # Width in dp
screenHeightDp=[height] # Height in dp
smallestScreenWidthDp=[size] # Smallest width
densityDpi=[dpi] # Screen density

}

Data Types and Formats

Field Type Format Example
Package name String Reverse domain com.example.app
Timestamp Long Milliseconds since epoch 1705363200000
Duration Long Milliseconds 3600000 (1 hour)
Event type Integer Event code 1 (ACTIVITY_RESUMED)
Launch count Integer Counter 42
Standby bucket Integer 10/20/30/40/45 10 (Active)
User ID Integer System user 0 (primary user)
Flags Hex Bitwise flags 0x0

Retention Periods

Aggregation Level Retention Period Interval Size
Daily 7 days 24 hours
Weekly 4 weeks 7 days
Monthly 6 months \~30 days
Yearly 2 years 365 days
Events Variable Individual events

Note: Actual retention may vary by Android version and available storage.

Sample Outputs with Annotations

Normal App Usage Pattern

package=com.android.chrome userId=0
totalTimeUsed=1847000 # 30.7 minutes total
lastTimeUsed=1705359842000 # 2024-01-15 22:04:02
appLaunchCount=8 # Launched 8 times
appStandbyBucket=10 # Active (used recently)

Events:
time=1705340400000 type=ACTIVITY_RESUMED package=com.android.chrome class=org.chromium.chrome.browser.ChromeTabbedActivity
time=1705340580000 type=USER_INTERACTION package=com.android.chrome # User actively using
time=1705340650000 type=ACTIVITY_PAUSED package=com.android.chrome # Switched away

# Duration: 250 seconds (4.2 minutes)

Suspicious Background Activity

package=com.unknown.service userId=0
totalTimeUsed=43200000 # 12 hours (suspicious!)
lastTimeUsed=1705361245000 # Recent activity
appLaunchCount=1 # Only launched once
appStandbyBucket=40 # Rare bucket (but high usage?)

Events:
time=1705318800000 type=ACTIVITY_RESUMED package=com.unknown.service
# No ACTIVITY_PAUSED event - still running?

# No USER_INTERACTION events - running without user input?

Hidden App Usage

package=com.hidden.calculator userId=0 # Calculator app name
totalTimeUsed=7200000 # 2 hours usage
lastTimeUsed=1705280400000 # Used at 3 AM
appLaunchCount=15 # Frequent launches

Events show file manager activities: # Suspicious!
time=1705280400000 type=ACTIVITY_RESUMED class=com.hidden.calculator.FileExplorerActivity

time=1705280420000 type=ACTIVITY_RESUMED class=com.hidden.calculator.PhotoVaultActivity

Quick Reference Commands

bash
# Essential Usage Statistics Commands
adb shell dumpsys usagestats # Full dump
adb shell dumpsys usagestats --hours 24 # Last 24 hours
adb shell dumpsys usagestats --days 7 # Last 7 days
adb shell dumpsys usagestats daily # Daily aggregations
adb shell dumpsys usagestats weekly # Weekly aggregations
adb shell dumpsys usagestats monthly # Monthly aggregations
adb shell dumpsys usagestats yearly # Yearly aggregations
adb shell dumpsys usagestats appstandby # App standby buckets
adb shell dumpsys usagestats eventstats # Raw event data

# Analysis Shortcuts
# Most used apps today
adb shell dumpsys usagestats --hours 24 | grep -B1 "totalTimeUsed=" | grep -v "=0"

# Recent app launches
adb shell dumpsys usagestats | grep "ACTIVITY_RESUMED" | tail -20

# Apps used at specific hour
adb shell dumpsys usagestats | grep "type=1" | grep "2024-01-15 14:"

# App standby states
adb shell dumpsys usagestats appstandby | grep -v "=40" # Non-rare apps

# Screen on/off correlation

adb shell dumpsys usagestats | grep -E "SCREEN_INTERACTIVE|SCREEN_NON_INTERACTIVE"

Understanding Usage Statistics Logs

Why Usage Statistics Logs Exist

Android introduced usage statistics in API 21 (Lollipop) to:

  1. System Optimization
  2. Manage app standby and battery optimization
  3. Predict user behavior for preloading
  4. Allocate resources based on usage patterns
  5. User Features
  6. Digital wellbeing and screen time tracking
  7. App usage limits and parental controls
  8. Personalized app suggestions
  9. Developer Analytics
  10. App engagement metrics
  11. Feature usage tracking
  12. Performance optimization data

How Android Generates Usage Data

Data Collection Flow

User Interaction

Activity Manager notifies Usage Stats Service

├── Component State Changes (foreground/background)
├── User Input Events (touches, clicks)
├── System Events (screen on/off)
└── Configuration Changes

In-Memory Event Buffer

Periodic Flush to Database

Aggregation into Time Buckets

Event Generation Triggers

  1. App Launch: Creates ACTIVITY_RESUMED event
  2. App Switch: ACTIVITY_PAUSED + new ACTIVITY_RESUMED
  3. User Touch: USER_INTERACTION events
  4. Screen State: SCREEN_INTERACTIVE/NON_INTERACTIVE
  5. Day Boundary: END_OF_DAY event at midnight

Data Storage Architecture

/data/system/usagestats/
├── 0/ # User 0 directory
│ ├── daily/ # Daily stats
│ │ ├── 1705276800000 # Timestamp files
│ │ └── 1705363200000
│ ├── weekly/ # Weekly aggregations
│ ├── monthly/ # Monthly aggregations
│ ├── yearly/ # Yearly aggregations

│ └── version # Database version

Forensic Significance

Critical Timeline Evidence

  1. User Presence Indicators
  2. Screen on/off events prove physical access
  3. USER_INTERACTION events show active use
  4. Keystroke patterns indicate user behavior
  5. App Usage Patterns
  6. Establishes daily routines
  7. Shows communication app usage times
  8. Reveals hidden or suspicious app activity
  9. Alibi Verification
  10. Precise timestamps for user activity
  11. Correlation with claimed activities
  12. Device usage during critical times
  13. Behavioral Analysis
  14. Sleep patterns from usage gaps
  15. Work/personal app usage separation
  16. Addiction or obsessive usage patterns

Investigative Applications

Investigation Type Relevant Usage Data
Timeline Reconstruction Event timestamps, app sequences
User Attribution Interaction events, usage patterns
Communication Analysis Messaging app usage times
Location Correlation Map app usage before movement
Contraband Detection Hidden app usage, vault apps
Child Safety Age-inappropriate app usage
Corporate Espionage Work app usage outside hours

Relationship to Other Logs

Direct Correlations

Usage Stats ←→ Battery Stats
└─ Foreground time links to battery drain

Usage Stats ←→ Notification Logs
└─ NOTIFICATION_SEEN events match notifications

Usage Stats ←→ Package Manager
└─ Package names validate installed apps

Usage Stats ←→ Activity Manager

└─ Component names match running activities

Powerful Correlation Techniques

Location Intelligence
bash
# Map app usage before location changes
# Extract map app usage
grep -E "maps|waze|navigation" usagestats_full.txt | \
grep "ACTIVITY_RESUMED" > navigation_usage.txt

# Correlate with location service usage

  1. adb shell dumpsys location | grep -A5 "Last Known Locations"

Communication Patterns
bash
# Message app usage vs network activity
COMM_APPS="whatsapp|telegram|signal|messages"
grep -E "$COMM_APPS" usagestats_full.txt | \
grep -E "RESUMED|PAUSED" > comm_timeline.txt

# Match with network data transfers

  1. adb shell dumpsys netstats | grep -E "$COMM_APPS" -A10

Deception Detection
bash
# Find app usage that contradicts user claims
# User claims sleeping 10 PM - 6 AM
awk '
/type=ACTIVITY_RESUMED/ {
match($0, /time=([0-9]+)/, t)
hour \= strftime("%H", t[1]/1000)
if (hour >= "22" || hour \<= "06") {
print strftime("%Y-%m-%d %H:%M:%S", t[1]/1000), $0
}
}

  1. ' usagestats_full.txt > night_activity.txt
  1. Scope Limitations
  2. Only shows app-level activity, not content
  3. Protected by usage access permission
  4. May require specific warrant language
  5. User Expectation
  6. Users often unaware of detailed tracking
  7. Digital wellbeing features make it visible
  8. Consider privacy implications in reports

Evidentiary Value

Strengths:

  • System-generated, difficult to forge
  • Millisecond precision timestamps
  • Multiple corroborating data points
  • Survives app uninstall

Limitations:

  • Can be cleared with factory reset
  • Requires usage access permission
  • May not capture all background activity
  • Multi-user devices complicate attribution

Court Presentation Tips

bash
# Create visual timeline for court
awk '/ACTIVITY_RESUMED/ {
match($0, /time=([0-9]+)/, t)
match($0, /package=([^ ]+)/, p)
printf "%s,%s,start\n", t[1], p[1]
}
/ACTIVITY_PAUSED/ {
match($0, /time=([0-9]+)/, t)
match($0, /package=([^ ]+)/, p)
printf "%s,%s,end\n", t[1], p[1]

}' usagestats_full.txt > timeline_for_visualization.csv

Common Challenges and Solutions

Challenge Solution
Permission denied Enable usage access in settings
Missing historical data Check retention periods, may be aged out
Time zone confusion Events in device local time, not UTC
Multi-user devices Filter by userId field
Background vs foreground Check event types carefully
App name obfuscation Cross-reference with package manager

Advanced Analysis Techniques

User Routine Profiling

python
#!/usr/bin/env python3
# profile_user_routine.py

import re
from collections import defaultdict
from datetime import datetime

# Parse usage events
events \= defaultdict(lambda: defaultdict(int))

with open('usagestats_full.txt', 'r') as f:
for line in f:
if 'ACTIVITY_RESUMED' in line:
time_match \= re.search(r'time=(\d+)', line)
pkg_match \= re.search(r'package=(\S+)', line)

        if time\_match and pkg\_match:  
            timestamp \= int(time\_match.group(1))  
            package \= pkg\_match.group(1)

            dt \= datetime.fromtimestamp(timestamp/1000)  
            hour \= dt.hour  
            weekday \= dt.strftime('%A')

            events\[weekday\]\[hour\] \+= 1

# Generate routine profile
print("User Activity Profile by Day and Hour:")
days \= ['Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday', 'Sunday']

for day in days:
print(f"\n{day}:")
for hour in range(24):
count \= events[day][hour]
bar \= '█' * (count // 5) # Scale for display

    print(f"  {hour:02d}:00 {bar} ({count} events)")

Hidden App Detection

bash
# Find calculator/utility apps with suspicious usage patterns
UTILITY_APPS="calculator|flashlight|notepad|clock"

awk -v apps="$UTILITY_APPS" '
$0 \~ apps && /package=/ {
current_app \= $0
gsub(/.*package=/, "", current_app)
gsub(/ .*/, "", current_app)
}
/totalTimeUsed=/ && current_app {
time \= $0
gsub(/.*totalTimeUsed=/, "", time)
gsub(/ .*/, "", time)
if (time > 600000) { # More than 10 minutes
printf "SUSPICIOUS: %s used for %d minutes\n",
current_app, time/60000
}
current_app \= ""
}

' usagestats_full.txt > suspicious_utility_usage.txt

App Dependency Analysis

bash
# Find apps that are always used together
awk '
/ACTIVITY_RESUMED/ {
match($0, /time=([0-9]+)/, t)
match($0, /package=([^ ]+)/, p)

if (last\_time && (t\[1\] \- last\_time) \< 30000\) {  \# Within 30 seconds  
  pair \= (last\_pkg \< p\[1\]) ? last\_pkg "+" p\[1\] : p\[1\] "+" last\_pkg  
  pairs\[pair\]++  
}

last\_time \= t\[1\]  
last\_pkg \= p\[1\]

}
END {
print "Frequently Used App Pairs:"
for (pair in pairs) {
if (pairs[pair] > 5) {
print pairs[pair] " times: " pair
}
}
}

' usagestats_full.txt | sort -nr > app_pairs.txt