1 package com.android.hotspot2.osu.service; 2 3 import android.content.Context; 4 import android.os.Handler; 5 import android.util.Log; 6 7 import com.android.hotspot2.Utils; 8 import com.android.hotspot2.WifiNetworkAdapter; 9 import com.android.hotspot2.osu.OSUManager; 10 import com.android.hotspot2.pps.HomeSP; 11 12 import org.xml.sax.SAXException; 13 14 import java.io.IOException; 15 import java.util.Collection; 16 import java.util.HashMap; 17 import java.util.Map; 18 19 public class SubscriptionTimer implements Runnable { 20 private final Handler mHandler; 21 private final OSUManager mOSUManager; 22 private final WifiNetworkAdapter mWifiNetworkAdapter; 23 private final Map<HomeSP, UpdateAction> mOutstanding = new HashMap<>(); 24 25 private static class UpdateAction { 26 private final long mRemediation; 27 private final long mPolicy; 28 29 private UpdateAction(HomeSP homeSP, long now) { 30 mRemediation = homeSP.getSubscriptionUpdate() != null ? 31 now + homeSP.getSubscriptionUpdate().getInterval() : -1; 32 mPolicy = homeSP.getPolicy() != null ? 33 now + homeSP.getPolicy().getPolicyUpdate().getInterval() : -1; 34 35 Log.d(OSUManager.TAG, "Timer set for " + homeSP.getFQDN() + 36 ", remediation: " + Utils.toUTCString(mRemediation) + 37 ", policy: " + Utils.toUTCString(mPolicy)); 38 } 39 40 private boolean remediate(long now) { 41 return mRemediation > 0 && now >= mRemediation; 42 } 43 44 private boolean policyUpdate(long now) { 45 return mPolicy > 0 && now >= mPolicy; 46 } 47 48 private long nextExpiry(long now) { 49 long min = Long.MAX_VALUE; 50 if (mRemediation > now) { 51 min = mRemediation; 52 } 53 if (mPolicy > now) { 54 min = Math.min(min, mPolicy); 55 } 56 return min; 57 } 58 } 59 60 private static final String ACTION_TIMER = 61 "com.android.hotspot2.osu.service.SubscriptionTimer.action.TICK"; 62 63 public SubscriptionTimer(OSUManager osuManager, 64 WifiNetworkAdapter wifiNetworkAdapter, Context context) { 65 mOSUManager = osuManager; 66 mWifiNetworkAdapter = wifiNetworkAdapter; 67 mHandler = new Handler(); 68 } 69 70 @Override 71 public void run() { 72 checkUpdates(); 73 } 74 75 public void checkUpdates() { 76 mHandler.removeCallbacks(this); 77 long now = System.currentTimeMillis(); 78 long next = Long.MAX_VALUE; 79 Collection<HomeSP> homeSPs = mWifiNetworkAdapter.getLoadedSPs(); 80 if (homeSPs.isEmpty()) { 81 return; 82 } 83 for (HomeSP homeSP : homeSPs) { 84 UpdateAction updateAction = mOutstanding.get(homeSP); 85 try { 86 if (updateAction == null) { 87 updateAction = new UpdateAction(homeSP, now); 88 mOutstanding.put(homeSP, updateAction); 89 } else if (updateAction.remediate(now)) { 90 mOSUManager.remediate(homeSP, false); 91 mOutstanding.put(homeSP, new UpdateAction(homeSP, now)); 92 } else if (updateAction.policyUpdate(now)) { 93 mOSUManager.remediate(homeSP, true); 94 mOutstanding.put(homeSP, new UpdateAction(homeSP, now)); 95 } 96 next = Math.min(next, updateAction.nextExpiry(now)); 97 } catch (IOException | SAXException e) { 98 Log.d(OSUManager.TAG, "Failed subscription update: " + e.getMessage()); 99 } 100 } 101 setAlarm(next); 102 } 103 104 private void setAlarm(long tod) { 105 long delay = tod - System.currentTimeMillis(); 106 mHandler.postAtTime(this, Math.max(1, delay)); 107 } 108 } 109