From e6cb8d6359a0334ac8f0e98ba2d850f7c84e4829 Mon Sep 17 00:00:00 2001 From: Jamorham Date: Tue, 23 Jul 2024 16:10:07 +0000 Subject: [PATCH] xDripSync: replacement for GCM fix --- .../eveningoutpost/dexdrip/GcmActivity.java | 13 ++- .../dexdrip/GcmListenerSvc.java | 4 +- .../dexdrip/cloud/jamcm/JamCm.java | 103 ++++++++++++++++++ 3 files changed, 113 insertions(+), 7 deletions(-) create mode 100644 app/src/main/java/com/eveningoutpost/dexdrip/cloud/jamcm/JamCm.java diff --git a/app/src/main/java/com/eveningoutpost/dexdrip/GcmActivity.java b/app/src/main/java/com/eveningoutpost/dexdrip/GcmActivity.java index 447dfef44f..be2e219f6e 100644 --- a/app/src/main/java/com/eveningoutpost/dexdrip/GcmActivity.java +++ b/app/src/main/java/com/eveningoutpost/dexdrip/GcmActivity.java @@ -16,6 +16,7 @@ import android.widget.Toast; +import com.eveningoutpost.dexdrip.cloud.jamcm.JamCm; import com.eveningoutpost.dexdrip.models.BgReading; import com.eveningoutpost.dexdrip.models.BloodTest; import com.eveningoutpost.dexdrip.models.Calibration; @@ -216,7 +217,8 @@ private static void queueCheckOld(Context context, boolean recursive) { try { Log.i(TAG, "Resending unacknowledged queue item: " + datum.bundle.getString("action") + datum.bundle.getString("payload")); datum.resent++; - GoogleCloudMessaging.getInstance(context).send(senderid + "@gcm.googleapis.com", Integer.toString(msgId.incrementAndGet()), datum.bundle); + // GoogleCloudMessaging.getInstance(context).send(senderid + "@gcm.googleapis.com", Integer.toString(msgId.incrementAndGet()), datum.bundle); + JamCm.sendMessage(datum.bundle); } catch (Exception e) { Log.e(TAG, "Got exception during resend: " + e.toString()); } @@ -650,7 +652,7 @@ public static void push_external_status_update(long timestamp, String statusLine } } - static String myIdentity() { + public static String myIdentity() { // TODO prefs override possible return GoogleDriveInterface.getDriveIdentityString(); } @@ -762,19 +764,20 @@ private static synchronized String sendMessageNow(String identity, String action Log.e(TAG, "Queue size exceeded"); Home.toaststaticnext("Maximum Sync Queue size Exceeded!"); } - final GoogleCloudMessaging gcm = GoogleCloudMessaging.getInstance(xdrip.getAppContext()); + // final GoogleCloudMessaging gcm = GoogleCloudMessaging.getInstance(xdrip.getAppContext()); if (token == null) { Log.e(TAG, "GCM token is null - cannot sendMessage"); return ""; } String messageid = Integer.toString(msgId.incrementAndGet()); - gcm.send(senderid + "@gcm.googleapis.com", messageid, data); + // gcm.send(senderid + "@gcm.googleapis.com", messageid, data); if (last_ack == -1) last_ack = JoH.tsl(); last_send_previous = last_send; last_send = JoH.tsl(); + JamCm.sendMessage(data); msg = "Sent message OK " + messageid; DesertSync.fromGCM(data); - } catch (IOException ex) { + } catch (Exception ex) { msg = "Error :" + ex.getMessage(); } Log.d(TAG, "Return msg in SendMessage: " + msg); diff --git a/app/src/main/java/com/eveningoutpost/dexdrip/GcmListenerSvc.java b/app/src/main/java/com/eveningoutpost/dexdrip/GcmListenerSvc.java index 0e2211199d..8e526d4cf6 100644 --- a/app/src/main/java/com/eveningoutpost/dexdrip/GcmListenerSvc.java +++ b/app/src/main/java/com/eveningoutpost/dexdrip/GcmListenerSvc.java @@ -16,6 +16,7 @@ import android.os.PowerManager; import android.util.Base64; +import com.eveningoutpost.dexdrip.cloud.jamcm.JamCm; import com.eveningoutpost.dexdrip.models.BgReading; import com.eveningoutpost.dexdrip.models.BloodTest; import com.eveningoutpost.dexdrip.models.Calibration; @@ -167,8 +168,7 @@ public void onMessageReceived(RemoteMessage rmessage) { String xfrom = data.getString("xfrom"); String payload = data.getString("datum", data.getString("payload")); String action = data.getString("action"); - - if ((xfrom != null) && (xfrom.equals(GcmActivity.token))) { + if ((xfrom != null) && (xfrom.equals(GcmActivity.token) || xfrom.equals(JamCm.getId()))) { GcmActivity.queueAction(action + payload); return; } diff --git a/app/src/main/java/com/eveningoutpost/dexdrip/cloud/jamcm/JamCm.java b/app/src/main/java/com/eveningoutpost/dexdrip/cloud/jamcm/JamCm.java new file mode 100644 index 0000000000..0162ff2d77 --- /dev/null +++ b/app/src/main/java/com/eveningoutpost/dexdrip/cloud/jamcm/JamCm.java @@ -0,0 +1,103 @@ +package com.eveningoutpost.dexdrip.cloud.jamcm; + +import static com.eveningoutpost.dexdrip.utils.CipherUtils.hexToBytes; + +import android.os.Bundle; + +import com.eveningoutpost.dexdrip.GcmActivity; +import com.eveningoutpost.dexdrip.models.JoH; +import com.eveningoutpost.dexdrip.models.UserError; +import com.eveningoutpost.dexdrip.utils.CipherUtils; + +import java.net.DatagramPacket; +import java.net.DatagramSocket; +import java.net.InetAddress; +import java.nio.ByteBuffer; +import java.nio.ByteOrder; +import java.nio.charset.StandardCharsets; + +import lombok.val; + +/** + * JamOrHam + *

+ * Replacement for GCM + */ +public class JamCm { + + private static final String TAG = "JamCm"; + private static final String serverInstance = "jamcm3749021"; + private static final String serverDomain = "bluejay.website"; + private static final String serverAddress = serverInstance + "." + serverDomain; + private static final int serverPort = 5228; + + private static final byte PROTOCOL_VERSION = 1; + + /** + * @noinspection DataFlowIssue + */ + public static String getId() { + if (GcmActivity.token == null) { + return null; + } + try { + return CipherUtils.getSHA256(GcmActivity.token).substring(0, 32); + } catch (Exception e) { + UserError.Log.wtf(TAG, "Got exception in getId: " + e); + return null; + } + } + + /** + * @noinspection DataFlowIssue + */ + public static void sendMessage(Bundle input) { + + val ids = getId(); + if (ids == null) { + if (JoH.ratelimit("sendMessage error", 1200)) { + UserError.Log.wtf(TAG, "Cannot send message due to missing id"); + } + return; + } + try { + UserError.Log.d(TAG, "sendMessage called"); + InetAddress address = InetAddress.getByName(serverAddress); + + byte[] id = hexToBytes(ids); + if (id.length != 16) { + throw new RuntimeException("Invalid id length: " + id.length); + } + byte[] channel = GcmActivity.myIdentity().getBytes(StandardCharsets.UTF_8); + if (channel.length != 32) { + throw new RuntimeException("Invalid channel length: " + channel.length); + } + + byte[] type = new byte[16]; + byte[] actionb = input.getString("action").getBytes(StandardCharsets.UTF_8); + System.arraycopy(actionb, 0, type, 0, Math.min(type.length, actionb.length)); + byte[] payload = input.getString("payload").getBytes(StandardCharsets.UTF_8); + short messageSize = (short) payload.length; + + val buffer = ByteBuffer.allocate(1 + 16 + 32 + 16 + 2 + payload.length); + buffer.order(ByteOrder.LITTLE_ENDIAN); + buffer.put(PROTOCOL_VERSION); + buffer.put(id); + buffer.put(channel); + buffer.put(type); + buffer.putShort(messageSize); + buffer.put(payload); + + val data = buffer.array(); + val packet = new DatagramPacket(data, data.length, address, serverPort); + + try (DatagramSocket socket = new DatagramSocket()) { + socket.send(packet); + UserError.Log.d(TAG, "Message sent to server"); + } + } catch (Exception e) { + UserError.Log.e(TAG, "Error: " + e); + } + } + +}