Loading play-services-core/src/main/AndroidManifest.xml +1 −3 Original line number Diff line number Diff line Loading @@ -198,8 +198,6 @@ <intent-filter> <action android:name="android.intent.action.BOOT_COMPLETED" /> <action android:name="android.intent.action.AIRPLANE_MODE" /> <action android:name="android.net.conn.CONNECTIVITY_CHANGE" /> <action android:name="android.net.conn.BACKGROUND_DATA_SETTING_CHANGED" /> <action android:name="android.server.checkin.CHECKIN" /> Loading Loading @@ -478,7 +476,7 @@ android:name="org.microg.gms.ui.AskPushPermission" android:excludeFromRecents="true" android:process=":ui" android:theme="@style/Theme.AppCompat.DayNight.Dialog.Alert" /> android:theme="@style/Theme.AppCompat.DayNight.Dialog.Alert.NoActionBar" /> <activity android:name="org.microg.gms.ui.AboutFragment$AsActivity" Loading play-services-core/src/main/java/org/microg/gms/checkin/CheckinService.java +15 −1 Original line number Diff line number Diff line Loading @@ -18,14 +18,16 @@ package org.microg.gms.checkin; import android.accounts.Account; import android.accounts.AccountManager; import android.app.Activity; import android.app.AlarmManager; import android.app.IntentService; import android.app.PendingIntent; import android.content.Context; import android.content.Intent; import android.os.Bundle; import android.os.IBinder; import android.os.RemoteException; import android.preference.PreferenceManager; import android.os.ResultReceiver; import android.util.Log; import androidx.legacy.content.WakefulBroadcastReceiver; Loading @@ -39,11 +41,15 @@ import org.microg.gms.people.PeopleManager; public class CheckinService extends IntentService { private static final String TAG = "GmsCheckinSvc"; public static final long MAX_VALID_CHECKIN_AGE = 24 * 60 * 60 * 1000; // 12 hours public static final long REGULAR_CHECKIN_INTERVAL = 12 * 60 * 60 * 1000; // 12 hours public static final long BACKUP_CHECKIN_DELAY = 3 * 60 * 60 * 1000; // 3 hours public static final String BIND_ACTION = "com.google.android.gms.checkin.BIND_TO_SERVICE"; public static final String EXTRA_FORCE_CHECKIN = "force"; @Deprecated public static final String EXTRA_CALLBACK_INTENT = "callback"; public static final String EXTRA_RESULT_RECEIVER = "receiver"; public static final String EXTRA_NEW_CHECKIN_TIME = "checkin_time"; private ICheckinService iface = new ICheckinService.Stub() { @Override Loading Loading @@ -73,6 +79,14 @@ public class CheckinService extends IntentService { if (intent.hasExtra(EXTRA_CALLBACK_INTENT)) { startService((Intent) intent.getParcelableExtra(EXTRA_CALLBACK_INTENT)); } if (intent.hasExtra(EXTRA_RESULT_RECEIVER)) { ResultReceiver receiver = intent.getParcelableExtra(EXTRA_RESULT_RECEIVER); if (receiver != null) { Bundle bundle = new Bundle(); bundle.putLong(EXTRA_NEW_CHECKIN_TIME, info.lastCheckin); receiver.send(Activity.RESULT_OK, bundle); } } } } } catch (Exception e) { Loading play-services-core/src/main/java/org/microg/gms/checkin/TriggerReceiver.java +3 −3 Original line number Diff line number Diff line Loading @@ -31,20 +31,20 @@ import static org.microg.gms.checkin.CheckinService.REGULAR_CHECKIN_INTERVAL; public class TriggerReceiver extends WakefulBroadcastReceiver { private static final String TAG = "GmsCheckinTrigger"; private static boolean registered = false; @Override public void onReceive(Context context, Intent intent) { try { boolean force = "android.provider.Telephony.SECRET_CODE".equals(intent.getAction()); ConnectivityManager cm = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE); if (CheckinPrefs.get(context).isEnabled() || force) { if (ConnectivityManager.CONNECTIVITY_ACTION.equals(intent.getAction()) && LastCheckinInfo.read(context).lastCheckin > System.currentTimeMillis() - REGULAR_CHECKIN_INTERVAL) { if (LastCheckinInfo.read(context).lastCheckin > System.currentTimeMillis() - REGULAR_CHECKIN_INTERVAL && !force) { CheckinService.schedule(context); return; } ConnectivityManager cm = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE); NetworkInfo networkInfo = cm.getActiveNetworkInfo(); if (networkInfo != null && networkInfo.isConnected() || force) { Intent subIntent = new Intent(context, CheckinService.class); Loading play-services-core/src/main/java/org/microg/gms/gcm/PushRegisterHandler.javadeleted 100644 → 0 +0 −193 Original line number Diff line number Diff line /* * Copyright (C) 2018 microG Project Team * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package org.microg.gms.gcm; import android.app.PendingIntent; import android.content.Context; import android.content.Intent; import android.os.Binder; import android.os.Bundle; import android.os.Handler; import android.os.Message; import android.os.Messenger; import android.os.RemoteException; import android.util.Log; import org.microg.gms.checkin.LastCheckinInfo; import org.microg.gms.common.ForegroundServiceContext; import org.microg.gms.common.PackageUtils; import org.microg.gms.common.Utils; import static org.microg.gms.gcm.GcmConstants.ACTION_C2DM_REGISTRATION; import static org.microg.gms.gcm.GcmConstants.ERROR_SERVICE_NOT_AVAILABLE; import static org.microg.gms.gcm.GcmConstants.EXTRA_APP; import static org.microg.gms.gcm.GcmConstants.EXTRA_APP_OVERRIDE; import static org.microg.gms.gcm.GcmConstants.EXTRA_ERROR; import static org.microg.gms.gcm.McsConstants.ACTION_ACK; import static org.microg.gms.gcm.McsConstants.ACTION_SEND; class PushRegisterHandler extends Handler { private static final String TAG = "GmsGcmRegisterHdl"; private Context context; private int callingUid; private GcmDatabase database; public PushRegisterHandler(Context context, GcmDatabase database) { this.context = context; this.database = database; } @Override public boolean sendMessageAtTime(Message msg, long uptimeMillis) { this.callingUid = Binder.getCallingUid(); return super.sendMessageAtTime(msg, uptimeMillis); } private void sendReplyViaMessage(int what, int id, Messenger replyTo, Bundle messageData) { Message response = Message.obtain(); response.what = what; response.arg1 = id; response.setData(messageData); try { replyTo.send(response); } catch (RemoteException e) { Log.w(TAG, e); } } private void sendReplyViaIntent(Intent outIntent, Messenger replyTo) { Message message = Message.obtain(); message.obj = outIntent; try { replyTo.send(message); } catch (RemoteException e) { Log.w(TAG, e); } } private void sendReply(int what, int id, Messenger replyTo, Bundle data, boolean oneWay) { if (what == 0) { Intent outIntent = new Intent(ACTION_C2DM_REGISTRATION); outIntent.putExtras(data); sendReplyViaIntent(outIntent, replyTo); return; } Bundle messageData = new Bundle(); messageData.putBundle("data", data); sendReplyViaMessage(what, id, replyTo, messageData); } private void replyError(int what, int id, Messenger replyTo, String errorMessage, boolean oneWay) { Bundle bundle = new Bundle(); bundle.putString(EXTRA_ERROR, errorMessage); sendReply(what, id, replyTo, bundle, oneWay); } private void replyNotAvailable(int what, int id, Messenger replyTo) { replyError(what, id, replyTo, ERROR_SERVICE_NOT_AVAILABLE, false); } private PendingIntent getSelfAuthIntent() { Intent intent = new Intent(); intent.setPackage("com.google.example.invalidpackage"); return PendingIntent.getBroadcast(context, 0, intent, 0); } @Override public void handleMessage(Message msg) { if (msg.what == 0) { if (msg.obj instanceof Intent) { Message nuMsg = Message.obtain(); nuMsg.what = msg.what; nuMsg.arg1 = 0; nuMsg.replyTo = null; PendingIntent pendingIntent = ((Intent) msg.obj).getParcelableExtra(EXTRA_APP); String packageName = PackageUtils.packageFromPendingIntent(pendingIntent); Bundle data = new Bundle(); data.putBoolean("oneWay", false); data.putString("pkg", packageName); data.putBundle("data", msg.getData()); nuMsg.setData(data); msg = nuMsg; } else { return; } } int what = msg.what; int id = msg.arg1; Messenger replyTo = msg.replyTo; if (replyTo == null) { Log.w(TAG, "replyTo is null"); return; } Bundle data = msg.getData(); String packageName = data.getString("pkg"); Bundle subdata = data.getBundle("data"); try { PackageUtils.checkPackageUid(context, packageName, callingUid); } catch (SecurityException e) { Log.w(TAG, e); return; } Log.d(TAG, "handleMessage: package=" + packageName + " what=" + what + " id=" + id); boolean oneWay = data.getBoolean("oneWay", false); switch (what) { case 0: case 1: // TODO: We should checkin and/or ask for permission here. String sender = subdata.getString("sender"); boolean delete = subdata.get("delete") != null; PushRegisterManager.completeRegisterRequest(context, database, new RegisterRequest() .build(Utils.getBuild(context)) .sender(sender) .checkin(LastCheckinInfo.read(context)) .app(packageName) .delete(delete) .extraParams(subdata), bundle -> sendReply(what, id, replyTo, bundle, oneWay)); break; case 2: String messageId = subdata.getString("google.message_id"); Log.d(TAG, "Ack " + messageId + " for " + packageName); Intent i = new Intent(context, McsService.class); i.setAction(ACTION_ACK); i.putExtra(EXTRA_APP, getSelfAuthIntent()); new ForegroundServiceContext(context).startService(i); break; default: Bundle bundle = new Bundle(); bundle.putBoolean("unsupported", true); sendReplyViaMessage(what, id, replyTo, bundle); return; } if (oneWay) { Bundle bundle = new Bundle(); bundle.putBoolean("ack", true); sendReplyViaMessage(what, id, replyTo, bundle); } } } play-services-core/src/main/java/org/microg/gms/gcm/PushRegisterReceiver.javadeleted 100644 → 0 +0 −41 Original line number Diff line number Diff line /* * Copyright (C) 2018 microG Project Team * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package org.microg.gms.gcm; import android.content.Context; import android.content.Intent; import androidx.legacy.content.WakefulBroadcastReceiver; import static org.microg.gms.gcm.GcmConstants.ACTION_C2DM_REGISTER; import static org.microg.gms.gcm.GcmConstants.ACTION_C2DM_UNREGISTER; public class PushRegisterReceiver extends WakefulBroadcastReceiver { private static final String TAG = "GmsGcmRegisterRcv"; @Override public void onReceive(Context context, Intent intent) { Intent intent2 = new Intent(context, PushRegisterService.class); if (intent.getExtras().get("delete") != null) { intent2.setAction(ACTION_C2DM_UNREGISTER); } else { intent2.setAction(ACTION_C2DM_REGISTER); } intent2.putExtras(intent.getExtras()); startWakefulService(context, intent2); } } Loading
play-services-core/src/main/AndroidManifest.xml +1 −3 Original line number Diff line number Diff line Loading @@ -198,8 +198,6 @@ <intent-filter> <action android:name="android.intent.action.BOOT_COMPLETED" /> <action android:name="android.intent.action.AIRPLANE_MODE" /> <action android:name="android.net.conn.CONNECTIVITY_CHANGE" /> <action android:name="android.net.conn.BACKGROUND_DATA_SETTING_CHANGED" /> <action android:name="android.server.checkin.CHECKIN" /> Loading Loading @@ -478,7 +476,7 @@ android:name="org.microg.gms.ui.AskPushPermission" android:excludeFromRecents="true" android:process=":ui" android:theme="@style/Theme.AppCompat.DayNight.Dialog.Alert" /> android:theme="@style/Theme.AppCompat.DayNight.Dialog.Alert.NoActionBar" /> <activity android:name="org.microg.gms.ui.AboutFragment$AsActivity" Loading
play-services-core/src/main/java/org/microg/gms/checkin/CheckinService.java +15 −1 Original line number Diff line number Diff line Loading @@ -18,14 +18,16 @@ package org.microg.gms.checkin; import android.accounts.Account; import android.accounts.AccountManager; import android.app.Activity; import android.app.AlarmManager; import android.app.IntentService; import android.app.PendingIntent; import android.content.Context; import android.content.Intent; import android.os.Bundle; import android.os.IBinder; import android.os.RemoteException; import android.preference.PreferenceManager; import android.os.ResultReceiver; import android.util.Log; import androidx.legacy.content.WakefulBroadcastReceiver; Loading @@ -39,11 +41,15 @@ import org.microg.gms.people.PeopleManager; public class CheckinService extends IntentService { private static final String TAG = "GmsCheckinSvc"; public static final long MAX_VALID_CHECKIN_AGE = 24 * 60 * 60 * 1000; // 12 hours public static final long REGULAR_CHECKIN_INTERVAL = 12 * 60 * 60 * 1000; // 12 hours public static final long BACKUP_CHECKIN_DELAY = 3 * 60 * 60 * 1000; // 3 hours public static final String BIND_ACTION = "com.google.android.gms.checkin.BIND_TO_SERVICE"; public static final String EXTRA_FORCE_CHECKIN = "force"; @Deprecated public static final String EXTRA_CALLBACK_INTENT = "callback"; public static final String EXTRA_RESULT_RECEIVER = "receiver"; public static final String EXTRA_NEW_CHECKIN_TIME = "checkin_time"; private ICheckinService iface = new ICheckinService.Stub() { @Override Loading Loading @@ -73,6 +79,14 @@ public class CheckinService extends IntentService { if (intent.hasExtra(EXTRA_CALLBACK_INTENT)) { startService((Intent) intent.getParcelableExtra(EXTRA_CALLBACK_INTENT)); } if (intent.hasExtra(EXTRA_RESULT_RECEIVER)) { ResultReceiver receiver = intent.getParcelableExtra(EXTRA_RESULT_RECEIVER); if (receiver != null) { Bundle bundle = new Bundle(); bundle.putLong(EXTRA_NEW_CHECKIN_TIME, info.lastCheckin); receiver.send(Activity.RESULT_OK, bundle); } } } } } catch (Exception e) { Loading
play-services-core/src/main/java/org/microg/gms/checkin/TriggerReceiver.java +3 −3 Original line number Diff line number Diff line Loading @@ -31,20 +31,20 @@ import static org.microg.gms.checkin.CheckinService.REGULAR_CHECKIN_INTERVAL; public class TriggerReceiver extends WakefulBroadcastReceiver { private static final String TAG = "GmsCheckinTrigger"; private static boolean registered = false; @Override public void onReceive(Context context, Intent intent) { try { boolean force = "android.provider.Telephony.SECRET_CODE".equals(intent.getAction()); ConnectivityManager cm = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE); if (CheckinPrefs.get(context).isEnabled() || force) { if (ConnectivityManager.CONNECTIVITY_ACTION.equals(intent.getAction()) && LastCheckinInfo.read(context).lastCheckin > System.currentTimeMillis() - REGULAR_CHECKIN_INTERVAL) { if (LastCheckinInfo.read(context).lastCheckin > System.currentTimeMillis() - REGULAR_CHECKIN_INTERVAL && !force) { CheckinService.schedule(context); return; } ConnectivityManager cm = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE); NetworkInfo networkInfo = cm.getActiveNetworkInfo(); if (networkInfo != null && networkInfo.isConnected() || force) { Intent subIntent = new Intent(context, CheckinService.class); Loading
play-services-core/src/main/java/org/microg/gms/gcm/PushRegisterHandler.javadeleted 100644 → 0 +0 −193 Original line number Diff line number Diff line /* * Copyright (C) 2018 microG Project Team * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package org.microg.gms.gcm; import android.app.PendingIntent; import android.content.Context; import android.content.Intent; import android.os.Binder; import android.os.Bundle; import android.os.Handler; import android.os.Message; import android.os.Messenger; import android.os.RemoteException; import android.util.Log; import org.microg.gms.checkin.LastCheckinInfo; import org.microg.gms.common.ForegroundServiceContext; import org.microg.gms.common.PackageUtils; import org.microg.gms.common.Utils; import static org.microg.gms.gcm.GcmConstants.ACTION_C2DM_REGISTRATION; import static org.microg.gms.gcm.GcmConstants.ERROR_SERVICE_NOT_AVAILABLE; import static org.microg.gms.gcm.GcmConstants.EXTRA_APP; import static org.microg.gms.gcm.GcmConstants.EXTRA_APP_OVERRIDE; import static org.microg.gms.gcm.GcmConstants.EXTRA_ERROR; import static org.microg.gms.gcm.McsConstants.ACTION_ACK; import static org.microg.gms.gcm.McsConstants.ACTION_SEND; class PushRegisterHandler extends Handler { private static final String TAG = "GmsGcmRegisterHdl"; private Context context; private int callingUid; private GcmDatabase database; public PushRegisterHandler(Context context, GcmDatabase database) { this.context = context; this.database = database; } @Override public boolean sendMessageAtTime(Message msg, long uptimeMillis) { this.callingUid = Binder.getCallingUid(); return super.sendMessageAtTime(msg, uptimeMillis); } private void sendReplyViaMessage(int what, int id, Messenger replyTo, Bundle messageData) { Message response = Message.obtain(); response.what = what; response.arg1 = id; response.setData(messageData); try { replyTo.send(response); } catch (RemoteException e) { Log.w(TAG, e); } } private void sendReplyViaIntent(Intent outIntent, Messenger replyTo) { Message message = Message.obtain(); message.obj = outIntent; try { replyTo.send(message); } catch (RemoteException e) { Log.w(TAG, e); } } private void sendReply(int what, int id, Messenger replyTo, Bundle data, boolean oneWay) { if (what == 0) { Intent outIntent = new Intent(ACTION_C2DM_REGISTRATION); outIntent.putExtras(data); sendReplyViaIntent(outIntent, replyTo); return; } Bundle messageData = new Bundle(); messageData.putBundle("data", data); sendReplyViaMessage(what, id, replyTo, messageData); } private void replyError(int what, int id, Messenger replyTo, String errorMessage, boolean oneWay) { Bundle bundle = new Bundle(); bundle.putString(EXTRA_ERROR, errorMessage); sendReply(what, id, replyTo, bundle, oneWay); } private void replyNotAvailable(int what, int id, Messenger replyTo) { replyError(what, id, replyTo, ERROR_SERVICE_NOT_AVAILABLE, false); } private PendingIntent getSelfAuthIntent() { Intent intent = new Intent(); intent.setPackage("com.google.example.invalidpackage"); return PendingIntent.getBroadcast(context, 0, intent, 0); } @Override public void handleMessage(Message msg) { if (msg.what == 0) { if (msg.obj instanceof Intent) { Message nuMsg = Message.obtain(); nuMsg.what = msg.what; nuMsg.arg1 = 0; nuMsg.replyTo = null; PendingIntent pendingIntent = ((Intent) msg.obj).getParcelableExtra(EXTRA_APP); String packageName = PackageUtils.packageFromPendingIntent(pendingIntent); Bundle data = new Bundle(); data.putBoolean("oneWay", false); data.putString("pkg", packageName); data.putBundle("data", msg.getData()); nuMsg.setData(data); msg = nuMsg; } else { return; } } int what = msg.what; int id = msg.arg1; Messenger replyTo = msg.replyTo; if (replyTo == null) { Log.w(TAG, "replyTo is null"); return; } Bundle data = msg.getData(); String packageName = data.getString("pkg"); Bundle subdata = data.getBundle("data"); try { PackageUtils.checkPackageUid(context, packageName, callingUid); } catch (SecurityException e) { Log.w(TAG, e); return; } Log.d(TAG, "handleMessage: package=" + packageName + " what=" + what + " id=" + id); boolean oneWay = data.getBoolean("oneWay", false); switch (what) { case 0: case 1: // TODO: We should checkin and/or ask for permission here. String sender = subdata.getString("sender"); boolean delete = subdata.get("delete") != null; PushRegisterManager.completeRegisterRequest(context, database, new RegisterRequest() .build(Utils.getBuild(context)) .sender(sender) .checkin(LastCheckinInfo.read(context)) .app(packageName) .delete(delete) .extraParams(subdata), bundle -> sendReply(what, id, replyTo, bundle, oneWay)); break; case 2: String messageId = subdata.getString("google.message_id"); Log.d(TAG, "Ack " + messageId + " for " + packageName); Intent i = new Intent(context, McsService.class); i.setAction(ACTION_ACK); i.putExtra(EXTRA_APP, getSelfAuthIntent()); new ForegroundServiceContext(context).startService(i); break; default: Bundle bundle = new Bundle(); bundle.putBoolean("unsupported", true); sendReplyViaMessage(what, id, replyTo, bundle); return; } if (oneWay) { Bundle bundle = new Bundle(); bundle.putBoolean("ack", true); sendReplyViaMessage(what, id, replyTo, bundle); } } }
play-services-core/src/main/java/org/microg/gms/gcm/PushRegisterReceiver.javadeleted 100644 → 0 +0 −41 Original line number Diff line number Diff line /* * Copyright (C) 2018 microG Project Team * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package org.microg.gms.gcm; import android.content.Context; import android.content.Intent; import androidx.legacy.content.WakefulBroadcastReceiver; import static org.microg.gms.gcm.GcmConstants.ACTION_C2DM_REGISTER; import static org.microg.gms.gcm.GcmConstants.ACTION_C2DM_UNREGISTER; public class PushRegisterReceiver extends WakefulBroadcastReceiver { private static final String TAG = "GmsGcmRegisterRcv"; @Override public void onReceive(Context context, Intent intent) { Intent intent2 = new Intent(context, PushRegisterService.class); if (intent.getExtras().get("delete") != null) { intent2.setAction(ACTION_C2DM_UNREGISTER); } else { intent2.setAction(ACTION_C2DM_REGISTER); } intent2.putExtras(intent.getExtras()); startWakefulService(context, intent2); } }