diff --git a/xwords4/android/app/src/main/AndroidManifest.xml b/xwords4/android/app/src/main/AndroidManifest.xml
index a86398fde..3a03fbc78 100644
--- a/xwords4/android/app/src/main/AndroidManifest.xml
+++ b/xwords4/android/app/src/main/AndroidManifest.xml
@@ -186,10 +186,6 @@
android:permission="android.permission.BIND_JOB_SERVICE"
android:exported="false"
/>
-
s_sentDied = new HashSet();
+
+ public static void handleFrom( Context context, byte[] buffer,
+ String phone, short port )
+ {
+ getCurReceiver( phone, port ).addPacket( context, buffer );
+ }
+
+ public static void onGameDictDownload( Context context, Intent intentOld )
+ {
+ }
+
+ public static void inviteRemote( Context context, String phone,
+ NetLaunchInfo nli )
+ {
+ getCurSender( phone ).addInvite( context, nli );
+ }
+
+ public static int sendPacket( Context context, String phone,
+ int gameID, byte[] binmsg )
+ {
+ getCurSender( phone ).addPacket( context, gameID, binmsg );
+ return binmsg.length;
+ }
+
+ public static void gameDied( Context context, int gameID, String phone )
+ {
+ getCurSender( phone ).addDeathNotice( context, gameID );
+ }
+
+ public static void stopService( Context context )
+ {
+ Log.d( TAG, "stopService() does nothing" );
+ }
+
+ private static boolean s_showToasts;
+ public static void smsToastEnable( boolean newVal )
+ {
+ s_showToasts = newVal;
+ }
+
+ public static class SMSPhoneInfo {
+ public SMSPhoneInfo( boolean isAPhone, String num, boolean gsm ) {
+ isPhone = isAPhone;
+ number = num;
+ isGSM = gsm;
+ }
+ public boolean isPhone;
+ public String number;
+ public boolean isGSM;
+ }
+
+ private static SMSPhoneInfo s_phoneInfo;
+ public static SMSPhoneInfo getPhoneInfo( Context context )
+ {
+ if ( null == s_phoneInfo ) {
+ try {
+ String number = null;
+ boolean isGSM = false;
+ boolean isPhone = false;
+ TelephonyManager mgr = (TelephonyManager)
+ context.getSystemService(Context.TELEPHONY_SERVICE);
+ if ( null != mgr ) {
+ number = mgr.getLine1Number(); // needs permission
+ int type = mgr.getPhoneType();
+ isGSM = TelephonyManager.PHONE_TYPE_GSM == type;
+ isPhone = true;
+ }
+
+ String radio =
+ XWPrefs.getPrefsString( context, R.string.key_force_radio );
+ int[] ids = { R.string.radio_name_real,
+ R.string.radio_name_tablet,
+ R.string.radio_name_gsm,
+ R.string.radio_name_cdma,
+ };
+
+ // default so don't crash before set
+ int id = R.string.radio_name_real;
+ for ( int ii = 0; ii < ids.length; ++ii ) {
+ if ( radio.equals(context.getString(ids[ii])) ) {
+ id = ids[ii];
+ break;
+ }
+ }
+
+ switch( id ) {
+ case R.string.radio_name_real:
+ break; // go with above
+ case R.string.radio_name_tablet:
+ number = null;
+ isPhone = false;
+ break;
+ case R.string.radio_name_gsm:
+ case R.string.radio_name_cdma:
+ isGSM = id == R.string.radio_name_gsm;
+ if ( null == number ) {
+ number = "000-000-0000";
+ }
+ isPhone = true;
+ break;
+ }
+
+ s_phoneInfo = new SMSPhoneInfo( isPhone, number, isGSM );
+ } catch ( SecurityException se ) {
+ Log.e( TAG, "got SecurityException" );
+ }
+ }
+ return s_phoneInfo;
+ }
+
+ public static void resetPhoneInfo()
+ {
+ s_phoneInfo = null;
+ }
+
+
+ private static class SendThread extends Thread {
+ private String mPhone;
+ private short mPort;
+ private LinkedBlockingQueue mQueue = new LinkedBlockingQueue<>();
+
+ SendThread( String phone ) {
+ mPhone = phone;
+ mPort = getNBSPort();
+ }
+
+ String getPhone() { return mPhone; }
+
+ void addPacket( Context context, int gameID, byte[] binmsg )
+ {
+ mQueue.add( new SendElem( context, SMS_CMD.DATA, gameID, binmsg ) );
+ }
+
+ void addInvite( Context context, NetLaunchInfo nli )
+ {
+ mQueue.add( new SendElem( context, SMS_CMD.INVITE, nli ) );
+ }
+
+ void addDeathNotice( Context context, int gameID )
+ {
+ mQueue.add( new SendElem( context, SMS_CMD.DEATH, gameID, null ) );
+ }
+
+ void addAck( Context context, int gameID )
+ {
+ mQueue.add( new SendElem( context, SMS_CMD.ACK_INVITE, gameID, null ) );
+ }
+
+ @Override
+ public void run() {
+ Log.d( TAG, "%s.run() starting for %s", this, mPhone );
+ int[] waitSecs = { 5 };
+
+ while ( !isInterrupted() ) {
+ SendElem elem;
+
+ try {
+ elem = mQueue.poll( waitSecs[0], TimeUnit.SECONDS );
+
+ byte[][] msgs;
+ if ( null == elem ) { // timed out?
+ // removeSelf( this );
+ msgs = XwJNI.smsproto_prepOutbound( SMS_CMD.NONE, 0, null, mPhone,
+ mPort, true, waitSecs );
+ } else {
+ boolean newSMSEnabled = XWPrefs.getSMSProtoEnabled( elem.context );
+ boolean forceNow = !newSMSEnabled; // || cmd == SMS_CMD.INVITE;
+ msgs = XwJNI.smsproto_prepOutbound( elem.cmd, elem.gameID, elem.data, mPhone,
+ mPort, forceNow, waitSecs );
+ }
+
+ if ( null != msgs ) {
+ sendBuffers( msgs, mPhone, mPort );
+ }
+ if ( waitSecs[0] <= 0 ) {
+ waitSecs[0] = 5;
+ }
+ } catch ( InterruptedException iex ) {
+ Log.d( TAG, "poll() threw: %s", iex.getMessage() );
+ break;
+ }
+ }
+
+ // To be safe, call again
+ removeSelf( this );
+
+ // Better not be leaving anything behind!
+ Assert.assertTrue( 0 == mQueue.size() || !BuildConfig.DEBUG );
+ Log.d( TAG, "%s.run() DONE", this );
+ }
+
+ private void sendBuffers( byte[][] fragments, String phone, short nbsPort )
+ {
+ Context context = XWApp.getContext();
+ boolean success = false;
+ if ( XWPrefs.getNBSEnabled( context ) ) {
+
+ // Try send-to-self
+ if ( XWPrefs.getSMSToSelfEnabled( context ) ) {
+ String myPhone = getPhoneInfo( context ).number;
+ if ( null != myPhone
+ && PhoneNumberUtils.compare( phone, myPhone ) ) {
+ for ( byte[] fragment : fragments ) {
+ handleFrom( context, fragment, phone, nbsPort );
+ }
+ success = true;
+ }
+ }
+
+ if ( !success ) {
+ try {
+ SmsManager mgr = SmsManager.getDefault();
+ boolean useProxy = Perms23.Perm.SEND_SMS.isBanned( context )
+ && NBSProxy.isInstalled( context );
+ PendingIntent sent = useProxy ? null
+ : makeStatusIntent( context, MSG_SENT );
+ PendingIntent delivery = useProxy ? null
+ : makeStatusIntent( context, MSG_DELIVERED );
+ for ( byte[] fragment : fragments ) {
+ if ( useProxy ) {
+ NBSProxy.send( context, phone, nbsPort, fragment );
+ } else {
+ mgr.sendDataMessage( phone, null, nbsPort, fragment,
+ sent, delivery );
+ }
+ }
+ success = true;
+ } catch ( IllegalArgumentException iae ) {
+ Log.w( TAG, "sendBuffers(%s): %s", phone, iae.toString() );
+ } catch ( NullPointerException npe ) {
+ Assert.assertFalse( BuildConfig.DEBUG ); // shouldn't be trying to do this!!!
+ } catch ( java.lang.SecurityException se ) {
+ // getHelper(context).postEvent( MultiEvent.SMS_SEND_FAILED_NOPERMISSION );
+ Assert.assertFalse( BuildConfig.DEBUG );
+ } catch ( Exception ee ) {
+ Log.ex( TAG, ee );
+ }
+ }
+ } else {
+ Log.i( TAG, "dropping because SMS disabled" );
+ }
+
+ // if ( showToasts( context ) && success && (0 == (++s_nSent % 5)) ) {
+ // DbgUtils.showf( context, "Sent msg %d", s_nSent );
+ // }
+
+ ConnStatusHandler.updateStatusOut( context, null,
+ CommsConnType.COMMS_CONN_SMS,
+ success );
+ }
+
+ private PendingIntent makeStatusIntent( Context context, String msg )
+ {
+ Intent intent = new Intent( msg );
+ return PendingIntent.getBroadcast( context, 0, intent, 0 );
+ }
+
+ private static class SendElem {
+ Context context;
+ SMS_CMD cmd;
+ int gameID;
+ byte[] data;
+ SendElem( Context context, SMS_CMD cmd, int gameID, byte[] data ) {
+ this.context = context;
+ this.cmd = cmd;
+ this.gameID = gameID;
+ this.data = data;
+ }
+ SendElem( Context context, SMS_CMD cmd, NetLaunchInfo nli ) {
+ this( context, cmd, 0, nli.asByteArray() );
+ }
+ }
+ }
+
+ private static Map sSendersMap = new HashMap<>();
+
+ private static SendThread getCurSender( String toPhone )
+ {
+ SendThread result = null;
+ synchronized ( sSendersMap ) {
+ result = sSendersMap.get( toPhone );
+ if ( result == null ) {
+ result = new SendThread( toPhone );
+ result.start();
+ sSendersMap.put( toPhone, result );
+ }
+ }
+ return result;
+ }
+
+ private static void removeSelf( SendThread self )
+ {
+ synchronized ( sSendersMap ) {
+ String phone = self.getPhone();
+ if ( sSendersMap.get(phone) == self ) {
+ sSendersMap.remove( phone );
+ }
+ }
+ }
+
+ private static class ReceiveThread extends Thread {
+ private String mPhone;
+ private short mPort;
+
+ private LinkedBlockingQueue mQueue = new LinkedBlockingQueue<>();
+
+ ReceiveThread( String fromPhone, short port ) {
+ mPhone = fromPhone;
+ mPort = port;
+ }
+
+ short getPort() { return mPort; }
+
+ void addPacket( Context context, byte[] data )
+ {
+ mQueue.add( new ReceiveElem( context, data ) );
+ }
+
+ @Override
+ public void run() {
+ Log.d( TAG, "%s.run() starting", this );
+ while ( ! isInterrupted() ) {
+ ReceiveElem elem;
+ try {
+ elem = mQueue.poll( 10, TimeUnit.SECONDS );
+
+ if ( null != elem ) {
+ SMSProtoMsg[] msgs = XwJNI.smsproto_prepInbound( elem.data, mPhone, mPort );
+ if ( null != msgs ) {
+ Log.d( TAG, "got %d msgs combined!", msgs.length );
+ for ( int ii = 0; ii < msgs.length; ++ii ) {
+ Log.d( TAG, "%d: type: %s; len: %d", ii, msgs[ii].cmd, msgs[ii].data.length );
+ }
+ for ( SMSProtoMsg msg : msgs ) {
+ receive( elem.context, msg );
+ }
+ getHelper(elem.context).postEvent( MultiEvent.SMS_RECEIVE_OK );
+ } else {
+ Log.d( TAG, "receiveBuffer(): bogus or incomplete message from %s",
+ mPhone );
+ }
+ }
+ } catch (InterruptedException iex) {
+ Log.d( TAG, "%s.poll() threw: %s", this, iex.getMessage() );
+ break;
+ }
+ }
+ Log.d( TAG, "%s.run() DONE", this );
+ }
+
+ private void receive( Context context, SMSProtoMsg msg )
+ {
+ Log.i( TAG, "receive(cmd=%s)", msg.cmd );
+ switch( msg.cmd ) {
+ case INVITE:
+ makeForInvite( context, NetLaunchInfo.makeFrom( context, msg.data ) );
+ break;
+ case DATA:
+ if ( feedMessage( context, msg.gameID, msg.data, new CommsAddrRec( mPhone ) ) ) {
+ SMSResendReceiver.resetTimer( context );
+ }
+ break;
+ case DEATH:
+ getHelper(context).postEvent( MultiEvent.MESSAGE_NOGAME, msg.gameID );
+ break;
+ case ACK_INVITE:
+ getHelper(context).postEvent( MultiEvent.NEWGAME_SUCCESS, msg.gameID );
+ break;
+ default:
+ Log.w( TAG, "unexpected cmd %s", msg.cmd );
+ Assert.assertFalse( BuildConfig.DEBUG );
+ break;
+ }
+ }
+
+ private boolean feedMessage( Context context, int gameID, byte[] msg,
+ CommsAddrRec addr )
+ {
+ XWServiceHelper.ReceiveResult rslt = getHelper(context)
+ .receiveMessage( gameID, null, msg, addr );
+ if ( XWServiceHelper.ReceiveResult.GAME_GONE == rslt ) {
+ sendDiedPacket( context, addr.sms_phone, gameID );
+ }
+ return rslt == XWServiceHelper.ReceiveResult.OK;
+ }
+
+ private void sendDiedPacket( Context context, String phone, int gameID )
+ {
+ if ( !s_sentDied.contains( gameID ) ) {
+ getCurSender( phone ).addDeathNotice( context, gameID );
+ // resendFor( phone, SMS_CMD.DEATH, gameID, null );
+ s_sentDied.add( gameID );
+ }
+ }
+
+ private void makeForInvite( Context context, NetLaunchInfo nli )
+ {
+ if ( nli != null ) {
+ getHelper(context).handleInvitation( nli, mPhone, DictFetchOwner.OWNER_SMS );
+ getCurSender( mPhone ).addAck( context, nli.gameID() );
+ }
+ }
+
+ private SMSServiceHelper mHelper = null;
+ private SMSServiceHelper getHelper( Context context )
+ {
+ if ( null == mHelper ) {
+ mHelper = new SMSServiceHelper( context );
+ }
+ return mHelper;
+ }
+
+ private static class ReceiveElem {
+ Context context;
+ byte[] data;
+ ReceiveElem( Context context, byte[] data )
+ {
+ this.context = context;
+ this.data = data;
+ }
+ }
+ }
+
+ private static Map sReceiversMap = new HashMap<>();
+ private static ReceiveThread getCurReceiver( String fromPhone, short port )
+ {
+ ReceiveThread result = null;
+ synchronized ( sReceiversMap ) {
+ result = sReceiversMap.get( fromPhone );
+ if ( result == null ) {
+ result = new ReceiveThread( fromPhone, port );
+ result.start();
+ sReceiversMap.put( fromPhone, result );
+ } else {
+ Assert.assertTrue( port == result.getPort() || !BuildConfig.DEBUG );
+ }
+ }
+ return result;
+ }
+
+ private static class SMSMsgSink extends MultiMsgSink {
+ private Context mContext;
+ public SMSMsgSink( Context context ) {
+ super( context );
+ mContext = context;
+ }
+
+ @Override
+ public int sendViaSMS( byte[] buf, int gameID, CommsAddrRec addr )
+ {
+ return sendPacket( mContext, addr.sms_phone, gameID, buf );
+ }
+ }
+
+ private static class SMSServiceHelper extends XWServiceHelper {
+ private Context mContext;
+
+ SMSServiceHelper( Context context ) {
+ super( context );
+ mContext = context;
+ }
+
+ @Override
+ protected MultiMsgSink getSink( long rowid )
+ {
+ return new SMSMsgSink( mContext );
+ }
+
+ @Override
+ protected void postNotification( String phone, int gameID, long rowid )
+ {
+ String owner = Utils.phoneToContact( mContext, phone, true );
+ String body = LocUtils.getString( mContext, R.string.new_name_body_fmt,
+ owner );
+ GameUtils.postInvitedNotification( mContext, gameID, body, rowid );
+ }
+ }
+
+ private static Short s_nbsPort = null;
+ private static short getNBSPort()
+ {
+ if ( null == s_nbsPort ) {
+ String asStr = XWApp.getContext().getString( R.string.nbs_port );
+ s_nbsPort = new Short((short)Integer.parseInt( asStr ) );
+ }
+ return s_nbsPort;
+ }
+}
diff --git a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/NetLaunchInfo.java b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/NetLaunchInfo.java
index 53c8a62f0..b2edc4f6c 100644
--- a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/NetLaunchInfo.java
+++ b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/NetLaunchInfo.java
@@ -591,7 +591,7 @@ public class NetLaunchInfo implements Serializable {
public void addSMSInfo( Context context )
{
- SMSService.SMSPhoneInfo pi = SMSService.getPhoneInfo( context );
+ NBSProto.SMSPhoneInfo pi = NBSProto.getPhoneInfo( context );
if ( null != pi ) {
phone = pi.number;
isGSM = pi.isGSM;
diff --git a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/PrefsDelegate.java b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/PrefsDelegate.java
index e9c60b1b8..b3239ca8b 100644
--- a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/PrefsDelegate.java
+++ b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/PrefsDelegate.java
@@ -189,11 +189,11 @@ public class PrefsDelegate extends DelegateBase
Log.enable( sp.getBoolean( key, false ) );
break;
case R.string.key_show_sms:
- SMSService.smsToastEnable( sp.getBoolean( key, false ) );
+ NBSProto.smsToastEnable( sp.getBoolean( key, false ) );
break;
case R.string.key_enable_nbs:
if ( ! sp.getBoolean( key, true ) ) {
- SMSService.stopService( m_activity );
+ NBSProto.stopService( m_activity );
}
break;
case R.string.key_download_path:
@@ -224,7 +224,7 @@ public class PrefsDelegate extends DelegateBase
forceDictsMatch( sp.getString( key, null ) );
break;
case R.string.key_force_radio:
- SMSService.resetPhoneInfo();
+ NBSProto.resetPhoneInfo();
break;
case R.string.key_disable_nag:
case R.string.key_disable_nag_solo:
diff --git a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/RelayService.java b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/RelayService.java
index 8fdffe282..7de48cf56 100644
--- a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/RelayService.java
+++ b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/RelayService.java
@@ -298,7 +298,7 @@ public class RelayService extends XWJIService
{
Log.d( TAG, "receiveInvitation: got nli from %d: %s", srcDevID,
nli.toString() );
- if ( !mHelper.handleInvitation( this, nli, null,
+ if ( !mHelper.handleInvitation( nli, null,
DictFetchOwner.OWNER_RELAY ) ) {
Log.d( TAG, "handleInvitation() failed" );
}
@@ -491,7 +491,7 @@ public class RelayService extends XWJIService
String msgNo = intent.getStringExtra( MSGNUM );
sendNoConnMessage( rowid, relayID, msg, msgNo, timestamp );
} else {
- mHelper.receiveMessage( this, rowid, null, msg, s_addr );
+ mHelper.receiveMessage( rowid, null, msg, s_addr );
}
break;
case INVITE:
@@ -1253,7 +1253,7 @@ public class RelayService extends XWJIService
long rowid = rowIDs[ii];
sink.setRowID( rowid );
for ( byte[] msg : forOne ) {
- mHelper.receiveMessage( this, rowid, sink, msg, s_addr );
+ mHelper.receiveMessage( rowid, sink, msg, s_addr );
}
}
}
diff --git a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/SMSReceiver.java b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/SMSReceiver.java
index b3f979866..a22c3b700 100644
--- a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/SMSReceiver.java
+++ b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/SMSReceiver.java
@@ -51,7 +51,8 @@ public class SMSReceiver extends BroadcastReceiver {
try {
String phone = sms.getOriginatingAddress();
byte[] body = sms.getUserData();
- SMSService.handleFrom( context, body, phone );
+ NBSProto.handleFrom( context, body, phone,
+ getConfiguredPort( context ) );
} catch ( NullPointerException npe ) {
Log.ex( TAG, npe );
}
diff --git a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/SMSService.java b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/SMSService.java
deleted file mode 100644
index dc942c39a..000000000
--- a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/SMSService.java
+++ /dev/null
@@ -1,670 +0,0 @@
-/* -*- compile-command: "find-and-gradle.sh inXw4Deb"; -*- */
-/*
- * Copyright 2010 - 2018 by Eric House (xwords@eehouse.org). All rights
- * reserved.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License as
- * published by the Free Software Foundation; either version 2 of the
- * License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful, but
- * WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
- */
-
-package org.eehouse.android.xw4;
-
-import android.app.Activity;
-import android.app.PendingIntent;
-import android.app.Service;
-import android.content.BroadcastReceiver;
-import android.content.Context;
-import android.content.Intent;
-import android.content.IntentFilter;
-import android.content.SharedPreferences;
-import android.content.SharedPreferences.OnSharedPreferenceChangeListener;
-import android.preference.PreferenceManager;
-import android.telephony.PhoneNumberUtils;
-import android.telephony.SmsManager;
-import android.telephony.TelephonyManager;
-
-import org.eehouse.android.nbsplib.NBSProxy;
-
-import org.eehouse.android.xw4.MultiService.DictFetchOwner;
-import org.eehouse.android.xw4.MultiService.MultiEvent;
-import org.eehouse.android.xw4.jni.CommsAddrRec;
-import org.eehouse.android.xw4.jni.CommsAddrRec.CommsConnType;
-import org.eehouse.android.xw4.jni.XwJNI;
-import org.eehouse.android.xw4.jni.XwJNI.SMSProtoMsg;
-import org.eehouse.android.xw4.jni.XwJNI.SMS_CMD;
-import org.eehouse.android.xw4.loc.LocUtils;
-
-import java.io.ByteArrayInputStream;
-import java.io.ByteArrayOutputStream;
-import java.io.DataInputStream;
-import java.io.DataOutputStream;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Iterator;
-import java.util.Map;
-import java.util.Set;
-
-public class SMSService extends XWJIService {
- private static final String TAG = SMSService.class.getSimpleName();
-
- private final static int sJobID = 218719980;
- static {
- XWJIService.register( SMSService.class, sJobID );
- }
-
- private static final String MSG_SENT = "MSG_SENT";
- private static final String MSG_DELIVERED = "MSG_DELIVERED";
-
- private static final int SMS_PROTO_VERSION_WITHPORT = 1;
- private static final int SMS_PROTO_VERSION = SMS_PROTO_VERSION_WITHPORT;
- private enum SMSAction implements XWJICmds { _NONE,
- INVITE,
- SEND,
- REMOVE,
- ADDED_MISSING,
- STOP_SELF,
- HANDLEDATA,
- RESEND,
- };
-
- private static final String CMD_STR = "CMD";
- private static final String BUFFER = "BUFFER";
- private static final String BINBUFFER = "BINBUFFER";
- private static final String PHONE = "PHONE";
- private static final String GAMEDATA_BA = "GD";
-
- private static final String PHONE_RECS_KEY =
- SMSService.class.getName() + "_PHONES";
-
- private static Boolean s_showToasts = null;
-
- private BroadcastReceiver m_sentReceiver;
- private BroadcastReceiver m_receiveReceiver;
- private OnSharedPreferenceChangeListener m_prefsListener;
- private SMSServiceHelper mHelper;
-
- private int m_nReceived = 0;
- private static int s_nSent = 0;
- private static Set s_sentDied = new HashSet();
-
- public static class SMSPhoneInfo {
- public SMSPhoneInfo( boolean isAPhone, String num, boolean gsm ) {
- isPhone = isAPhone;
- number = num;
- isGSM = gsm;
- }
- public boolean isPhone;
- public String number;
- public boolean isGSM;
- }
-
- private static SMSPhoneInfo s_phoneInfo;
- public static SMSPhoneInfo getPhoneInfo( Context context )
- {
- if ( null == s_phoneInfo ) {
- try {
- String number = null;
- boolean isGSM = false;
- boolean isPhone = false;
- TelephonyManager mgr = (TelephonyManager)
- context.getSystemService(Context.TELEPHONY_SERVICE);
- if ( null != mgr ) {
- number = mgr.getLine1Number(); // needs permission
- int type = mgr.getPhoneType();
- isGSM = TelephonyManager.PHONE_TYPE_GSM == type;
- isPhone = true;
- }
-
- String radio =
- XWPrefs.getPrefsString( context, R.string.key_force_radio );
- int[] ids = { R.string.radio_name_real,
- R.string.radio_name_tablet,
- R.string.radio_name_gsm,
- R.string.radio_name_cdma,
- };
-
- // default so don't crash before set
- int id = R.string.radio_name_real;
- for ( int ii = 0; ii < ids.length; ++ii ) {
- if ( radio.equals(context.getString(ids[ii])) ) {
- id = ids[ii];
- break;
- }
- }
-
- switch( id ) {
- case R.string.radio_name_real:
- break; // go with above
- case R.string.radio_name_tablet:
- number = null;
- isPhone = false;
- break;
- case R.string.radio_name_gsm:
- case R.string.radio_name_cdma:
- isGSM = id == R.string.radio_name_gsm;
- if ( null == number ) {
- number = "000-000-0000";
- }
- isPhone = true;
- break;
- }
-
- s_phoneInfo = new SMSPhoneInfo( isPhone, number, isGSM );
- } catch ( SecurityException se ) {
- Log.e( TAG, "got SecurityException" );
- }
- }
- return s_phoneInfo;
- }
-
- public static void resetPhoneInfo()
- {
- s_phoneInfo = null;
- }
-
- public static void smsToastEnable( boolean newVal )
- {
- s_showToasts = newVal;
- }
-
- public static void stopService( Context context )
- {
- Intent intent = getIntentTo( context, SMSAction.STOP_SELF );
- enqueueWork( context, intent );
- }
-
- // NBS case
- public static void handleFrom( Context context, byte[] buffer,
- String phone )
- {
- Intent intent = getIntentTo( context, SMSAction.HANDLEDATA )
- .putExtra( BUFFER, buffer )
- .putExtra( PHONE, phone );
- enqueueWork( context, intent );
- }
-
- public static void inviteRemote( Context context, String phone,
- NetLaunchInfo nli )
- {
- Log.w( TAG, "inviteRemote(%s, '%s')", phone, nli );
- byte[] data = nli.asByteArray();
- Intent intent = getIntentTo( context, SMSAction.INVITE )
- .putExtra( PHONE, phone )
- .putExtra( GAMEDATA_BA, data );
- enqueueWork( context, intent );
- }
-
- public static int sendPacket( Context context, String phone,
- int gameID, byte[] binmsg )
- {
- int nSent = -1;
- if ( XWPrefs.getNBSEnabled( context ) ) {
- Intent intent = getIntentTo( context, SMSAction.SEND )
- .putExtra( PHONE, phone )
- .putExtra( MultiService.GAMEID, gameID )
- .putExtra( BINBUFFER, binmsg );
- enqueueWork( context, intent );
- nSent = binmsg.length;
- } else {
- Log.i( TAG, "sendPacket: dropping because SMS disabled" );
- }
- Log.d( TAG, "sendPacket(len=%d) => %d", binmsg.length, nSent );
- return nSent;
- }
-
- public static void gameDied( Context context, int gameID, String phone )
- {
- Intent intent = getIntentTo( context, SMSAction.REMOVE )
- .putExtra( PHONE, phone )
- .putExtra( MultiService.GAMEID, gameID );
- enqueueWork( context, intent );
- }
-
- public static void onGameDictDownload( Context context, Intent intentOld )
- {
- Intent intent = getIntentTo( context, SMSAction.ADDED_MISSING );
- intent.fillIn( intentOld, 0 );
- enqueueWork( context, intent );
- }
-
- public static String fromPublicFmt( String msg )
- {
- String result = null;
- if ( null != msg && msg.startsWith( XWApp.SMS_PUBLIC_HEADER ) ) {
- // Number format exception etc. can result from malicious
- // messages. Be safe: use try;
- try {
- String tmp = msg.substring( 1 + msg.lastIndexOf( " " ) );
-
- int headerLen = XWApp.SMS_PUBLIC_HEADER.length();
- String hashString =
- msg.substring( headerLen, headerLen + 4 );
- int hashRead = Integer.parseInt( hashString, 16 );
- int hashCode = 0xFFFF & tmp.hashCode();
- if ( hashRead == hashCode ) {
- result = tmp;
- } else {
- Log.w( TAG, "fromPublicFmt: hash code mismatch" );
- }
- } catch( Exception e ) {
- }
- }
- return result;
- }
-
- private static void enqueueWork( Context context, Intent intent )
- {
- enqueueWork( context, SMSService.class, intent );
- Log.d( TAG, "called enqueueWork(%s)", intent );
- }
-
- private static Intent getIntentTo( Context context, SMSAction cmd )
- {
- return getIntentTo( context, SMSService.class, cmd );
- }
-
- private static boolean showToasts( Context context )
- {
- if ( null == s_showToasts ) {
- s_showToasts =
- XWPrefs.getPrefsBoolean( context, R.string.key_show_sms, false );
- }
- return s_showToasts;
- }
-
- @Override
- public void onCreate()
- {
- super.onCreate();
-
- mHelper = new SMSServiceHelper( this );
- if ( Utils.deviceSupportsNBS( this ) ) {
- registerReceivers();
- }
- }
-
- @Override
- XWJICmds[] getCmds() { return SMSAction.values(); }
-
- @Override
- void onHandleWorkImpl( Intent intent, XWJICmds jicmd, long timestamp )
- {
- Log.d( TAG, "onHandleWorkImpl()" );
- SMSAction cmd = (SMSAction)jicmd;
- switch( cmd ) {
- case STOP_SELF:
- stopSelf();
- break;
- case HANDLEDATA:
- ++m_nReceived;
- ConnStatusHandler.
- updateStatusIn( this, null,
- CommsConnType.COMMS_CONN_SMS, true );
- if ( showToasts( this ) && (0 == (m_nReceived % 5)) ) {
- DbgUtils.showf( this, "Got msg %d", m_nReceived );
- }
- String phone = intent.getStringExtra( PHONE );
- byte[] buffer = intent.getByteArrayExtra( BUFFER );
- receiveBuffer( buffer, phone );
- break;
- case INVITE:
- phone = intent.getStringExtra( PHONE );
- buffer = intent.getByteArrayExtra( GAMEDATA_BA );
- inviteRemote( phone, buffer );
- break;
- case ADDED_MISSING:
- NetLaunchInfo nli
- = MultiService.getMissingDictData( this, intent );
- phone = intent.getStringExtra( PHONE );
- makeForInvite( phone, nli );
- break;
- case SEND:
- phone = intent.getStringExtra( PHONE );
- byte[] bytes = intent.getByteArrayExtra( BINBUFFER );
- int gameID = intent.getIntExtra( MultiService.GAMEID, -1 );
- sendPacket( phone, gameID, bytes );
- break;
- case REMOVE:
- gameID = intent.getIntExtra( MultiService.GAMEID, -1 );
- phone = intent.getStringExtra( PHONE );
- sendDiedPacket( phone, gameID );
- break;
- case RESEND:
- phone = intent.getStringExtra( PHONE );
- resendFor( phone );
- }
- }
-
- @Override
- public void onDestroy()
- {
- if ( null != m_sentReceiver ) {
- unregisterReceiver( m_sentReceiver );
- m_sentReceiver = null;
- }
- if ( null != m_receiveReceiver ) {
- unregisterReceiver( m_receiveReceiver );
- m_receiveReceiver = null;
- }
- if ( null != m_prefsListener ) {
- SharedPreferences sp
- = PreferenceManager.getDefaultSharedPreferences( this );
- sp.unregisterOnSharedPreferenceChangeListener( m_prefsListener );
- m_prefsListener = null;
- }
-
- super.onDestroy();
- }
-
- private void inviteRemote( String phone, byte[] asBytes )
- {
- resendFor( phone, SMS_CMD.INVITE, 0, asBytes, true );
- }
-
- private void ackInvite( String phone, int gameID )
- {
- resendFor( phone, SMS_CMD.ACK_INVITE, gameID, null );
- }
-
- private void sendDiedPacket( String phone, int gameID )
- {
- if ( !s_sentDied.contains( gameID ) ) {
- resendFor( phone, SMS_CMD.DEATH, gameID, null );
- s_sentDied.add( gameID );
- }
- }
-
- public int sendPacket( String phone, int gameID, byte[] bytes )
- {
- resendFor( phone, SMS_CMD.DATA, gameID, bytes );
- return bytes.length;
- }
-
- private void sendOrRetry( byte[][] msgs, String toPhone, int waitSecs )
- {
- if ( null != msgs ) {
- sendBuffers( msgs, toPhone );
- }
- if ( waitSecs > 0 ) {
- // PENDING
- Log.d( TAG, "calling postResend(), but might want to avoid enqueueWork!" );
- postResend( toPhone, waitSecs );
- }
- }
-
- private void resendFor( String toPhone, SMS_CMD cmd, int gameID, byte[] data )
- {
- boolean newSMSEnabled = XWPrefs.getSMSProtoEnabled( this );
- boolean forceNow = !newSMSEnabled; // || cmd == SMS_CMD.INVITE;
- resendFor( toPhone, cmd, gameID, data, forceNow );
- }
-
- private void resendFor( String toPhone )
- {
- resendFor( toPhone, SMS_CMD.NONE, 0, null, false );
- }
-
- private void resendFor( String toPhone, SMS_CMD cmd, int gameID, byte[] data,
- boolean forceNow )
- {
- int[] waitSecs = { 0 };
- byte[][] msgs = XwJNI.smsproto_prepOutbound( cmd, gameID, data, toPhone,
- getNBSPort(), forceNow,
- waitSecs );
- sendOrRetry( msgs, toPhone, waitSecs[0] );
- }
-
- private void postResend( final String phone, final int waitSecs )
- {
- Log.d( TAG, "postResend" );
- new Thread( new Runnable() {
- @Override
- public void run() {
- try {
- Thread.sleep( waitSecs * 1000 );
-
- Log.d( TAG, "postResend.run()" );
- Intent intent = getIntentTo( SMSService.this,
- SMSAction.RESEND );
- intent.putExtra( PHONE, phone );
- enqueueWork( SMSService.this, intent );
- } catch ( InterruptedException ie ) {
- Log.e( TAG, ie.getMessage() );
- }
- }
- } ).start();
- }
-
- private void receive( SMSProtoMsg msg, String phone )
- {
- Log.i( TAG, "receive(cmd=%s)", msg.cmd );
- switch( msg.cmd ) {
- case INVITE:
- makeForInvite( phone, NetLaunchInfo.makeFrom( this, msg.data ) );
- break;
- case DATA:
- if ( feedMessage( msg.gameID, msg.data, new CommsAddrRec( phone ) ) ) {
- SMSResendReceiver.resetTimer( this );
- }
- break;
- case DEATH:
- mHelper.postEvent( MultiEvent.MESSAGE_NOGAME, msg.gameID );
- break;
- case ACK_INVITE:
- mHelper.postEvent( MultiEvent.NEWGAME_SUCCESS, msg.gameID );
- break;
- default:
- Log.w( TAG, "unexpected cmd %s", msg.cmd );
- Assert.assertFalse( BuildConfig.DEBUG );
- break;
- }
- }
-
- private void receiveBuffer( byte[] buffer, String senderPhone )
- {
- SMSProtoMsg[] msgs = XwJNI.smsproto_prepInbound( buffer, senderPhone,
- getNBSPort() );
- if ( null != msgs ) {
- for ( SMSProtoMsg msg : msgs ) {
- receive( msg, senderPhone );
- }
- mHelper.postEvent( MultiEvent.SMS_RECEIVE_OK );
- } else {
- Log.d( TAG, "receiveBuffer(): bogus or incomplete message from %s",
- senderPhone );
- }
- }
-
- private void makeForInvite( String phone, NetLaunchInfo nli )
- {
- if ( nli != null ) {
- mHelper.handleInvitation( this, nli, phone, DictFetchOwner.OWNER_SMS );
- ackInvite( phone, nli.gameID() );
- }
- }
-
- private PendingIntent makeStatusIntent( String msg )
- {
- Intent intent = new Intent( msg );
- return PendingIntent.getBroadcast( this, 0, intent, 0 );
- }
-
- private boolean sendBuffers( byte[][] fragments, String phone )
- {
- boolean success = false;
- if ( XWPrefs.getNBSEnabled( this ) ) {
-
- // Try send-to-self
- if ( XWPrefs.getSMSToSelfEnabled( this ) ) {
- String myPhone = getPhoneInfo( this ).number;
- if ( null != myPhone
- && PhoneNumberUtils.compare( phone, myPhone ) ) {
- for ( byte[] fragment : fragments ) {
- handleFrom( this, fragment, phone );
- }
- success = true;
- }
- }
-
- if ( !success ) {
- short nbsPort = getNBSPort();
- try {
- SmsManager mgr = SmsManager.getDefault();
- boolean useProxy = Perms23.Perm.SEND_SMS.isBanned( this )
- && NBSProxy.isInstalled( this );
- PendingIntent sent = useProxy ? null : makeStatusIntent( MSG_SENT );
- PendingIntent delivery = useProxy ? null : makeStatusIntent( MSG_DELIVERED );
- for ( byte[] fragment : fragments ) {
- if ( useProxy ) {
- NBSProxy.send( this, phone, nbsPort, fragment );
- } else {
- mgr.sendDataMessage( phone, null, nbsPort, fragment,
- sent, delivery );
- }
- // Log.i( TAG, "sendBuffers(): sent %d byte fragment to %s",
- // fragment.length, phone );
- }
- success = true;
- } catch ( IllegalArgumentException iae ) {
- Log.w( TAG, "sendBuffers(%s): %s", phone, iae.toString() );
- } catch ( NullPointerException npe ) {
- Assert.assertFalse( BuildConfig.DEBUG ); // shouldn't be trying to do this!!!
- } catch ( java.lang.SecurityException se ) {
- mHelper.postEvent( MultiEvent.SMS_SEND_FAILED_NOPERMISSION );
- } catch ( Exception ee ) {
- Log.ex( TAG, ee );
- }
- }
- } else {
- Log.i( TAG, "dropping because SMS disabled" );
- }
-
- if ( showToasts( this ) && success && (0 == (++s_nSent % 5)) ) {
- DbgUtils.showf( this, "Sent msg %d", s_nSent );
- }
-
- ConnStatusHandler.updateStatusOut( this, null,
- CommsConnType.COMMS_CONN_SMS,
- success );
- return success;
- }
-
- private boolean feedMessage( int gameID, byte[] msg, CommsAddrRec addr )
- {
- XWServiceHelper.ReceiveResult rslt = mHelper
- .receiveMessage( this, gameID, null, msg, addr );
- if ( XWServiceHelper.ReceiveResult.GAME_GONE == rslt ) {
- sendDiedPacket( addr.sms_phone, gameID );
- }
- return rslt == XWServiceHelper.ReceiveResult.OK;
- }
-
- private void registerReceivers()
- {
- m_sentReceiver = new BroadcastReceiver() {
- @Override
- public void onReceive(Context arg0, Intent arg1)
- {
- switch ( getResultCode() ) {
- case Activity.RESULT_OK:
- mHelper.postEvent( MultiEvent.SMS_SEND_OK );
- break;
- case SmsManager.RESULT_ERROR_RADIO_OFF:
- mHelper.postEvent( MultiEvent.SMS_SEND_FAILED_NORADIO );
- break;
- case SmsManager.RESULT_ERROR_NO_SERVICE:
- default:
- Log.w( TAG, "FAILURE!!!" );
- mHelper.postEvent( MultiEvent.SMS_SEND_FAILED );
- break;
- }
- }
- };
- registerReceiver( m_sentReceiver, new IntentFilter(MSG_SENT) );
-
- m_receiveReceiver = new BroadcastReceiver() {
- @Override
- public void onReceive( Context context, Intent intent )
- {
- if ( Activity.RESULT_OK != getResultCode() ) {
- Log.w( TAG, "SMS delivery result: FAILURE" );
- }
- }
- };
- registerReceiver( m_receiveReceiver, new IntentFilter(MSG_DELIVERED) );
- }
-
- private static String matchKeyIf( Map map, final String phone )
- {
- String result = phone;
- Set keys = map.keySet();
- if ( ! keys.contains( result ) ) {
- for ( Iterator iter = keys.iterator(); iter.hasNext(); ) {
- String key = iter.next();
- if ( PhoneNumberUtils.compare( key, phone ) ) {
- result = key;
- break;
- }
- }
- }
- Log.i( TAG, "matchKeyIf(%s) => %s", phone, result );
- return result;
- }
-
- private static Short s_nbsPort = null;
- private short getNBSPort()
- {
- if ( null == s_nbsPort ) {
- String asStr = getString( R.string.nbs_port );
- s_nbsPort = new Short((short)Integer.parseInt( asStr ) );
- }
- return s_nbsPort;
- }
-
- private class SMSMsgSink extends MultiMsgSink {
- public SMSMsgSink( Context context ) {
- super( context );
- }
-
- @Override
- public int sendViaSMS( byte[] buf, int gameID, CommsAddrRec addr )
- {
- return sendPacket( addr.sms_phone, gameID, buf );
- }
- }
-
- private class SMSServiceHelper extends XWServiceHelper {
- private Service mService;
-
- SMSServiceHelper( Service service ) {
- super( service );
- mService = service;
- }
-
- @Override
- protected MultiMsgSink getSink( long rowid )
- {
- return new SMSMsgSink( SMSService.this );
- }
-
- @Override
- protected void postNotification( String phone, int gameID, long rowid )
- {
- String owner = Utils.phoneToContact( mService, phone, true );
- String body = LocUtils.getString( mService, R.string.new_name_body_fmt,
- owner );
- GameUtils.postInvitedNotification( mService, gameID, body, rowid );
- }
- }
-}
diff --git a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/Utils.java b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/Utils.java
index c677b06a4..a89166cfc 100644
--- a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/Utils.java
+++ b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/Utils.java
@@ -126,7 +126,7 @@ public class Utils {
{
boolean result = false;
if ( Perms23.havePermissions( context, Perm.READ_PHONE_STATE ) ) {
- SMSService.SMSPhoneInfo info = SMSService.getPhoneInfo( context );
+ NBSProto.SMSPhoneInfo info = NBSProto.getPhoneInfo( context );
result = null != info && info.isPhone && info.isGSM;
}
Log.d( TAG, "isGSMPhone() => %b", result );
diff --git a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/WiDirService.java b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/WiDirService.java
index d9382b530..315f095c5 100644
--- a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/WiDirService.java
+++ b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/WiDirService.java
@@ -754,7 +754,7 @@ public class WiDirService extends XWService {
.setP2PParams( macAddress );
XWServiceHelper.ReceiveResult rslt = mHelper
- .receiveMessage( this, gameID, m_sink, data, addr );
+ .receiveMessage( gameID, m_sink, data, addr );
if ( XWServiceHelper.ReceiveResult.GAME_GONE == rslt ) {
sendNoGame( null, macAddress, gameID );
}
@@ -767,7 +767,7 @@ public class WiDirService extends XWService {
NetLaunchInfo nli = NetLaunchInfo.makeFrom( this, nliData );
String returnMac = intent.getStringExtra( KEY_SRC );
- if ( !mHelper.handleInvitation( this, nli, returnMac, DictFetchOwner.OWNER_P2P ) ) {
+ if ( !mHelper.handleInvitation( nli, returnMac, DictFetchOwner.OWNER_P2P ) ) {
Log.d( TAG, "handleInvitation() failed" );
}
}
diff --git a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/XWApp.java b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/XWApp.java
index 28673f063..c9fc6edb9 100644
--- a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/XWApp.java
+++ b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/XWApp.java
@@ -143,7 +143,7 @@ public class XWApp extends Application
public void onDataReceived( short port, String fromPhone, byte[] data )
{
Assert.assertTrue( port == mPort || !BuildConfig.DEBUG );
- SMSService.handleFrom( this, data, fromPhone );
+ NBSProto.handleFrom( this, data, fromPhone, port );
}
@Override
diff --git a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/XWServiceHelper.java b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/XWServiceHelper.java
index 06ece2e07..e86597e1f 100644
--- a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/XWServiceHelper.java
+++ b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/XWServiceHelper.java
@@ -38,31 +38,31 @@ import java.util.Map;
abstract class XWServiceHelper {
private static final String TAG = XWServiceHelper.class.getSimpleName();
- private Service mService;
+ private Context mContext;
private static MultiService s_srcMgr = new MultiService();
public static enum ReceiveResult { OK, GAME_GONE, UNCONSUMED };
- XWServiceHelper( Service service )
+ XWServiceHelper( Context context )
{
- mService = service;
+ mContext = context;
}
abstract MultiMsgSink getSink( long rowid );
abstract void postNotification( String device, int gameID, long rowid );
- protected ReceiveResult receiveMessage( Context context, int gameID,
+ protected ReceiveResult receiveMessage( int gameID,
MultiMsgSink sink, byte[] msg,
CommsAddrRec addr )
{
ReceiveResult result;
- long[] rowids = DBUtils.getRowIDsFor( context, gameID );
+ long[] rowids = DBUtils.getRowIDsFor( mContext, gameID );
if ( null == rowids || 0 == rowids.length ) {
result = ReceiveResult.GAME_GONE;
} else {
result = ReceiveResult.UNCONSUMED;
for ( long rowid : rowids ) {
- if ( receiveMessage( context, rowid, sink, msg, addr ) ) {
+ if ( receiveMessage( rowid, sink, msg, addr ) ) {
result = ReceiveResult.OK;
}
}
@@ -70,9 +70,8 @@ abstract class XWServiceHelper {
return result;
}
- protected boolean receiveMessage( Context context, long rowid,
- MultiMsgSink sink, byte[] msg,
- CommsAddrRec addr )
+ protected boolean receiveMessage( long rowid, MultiMsgSink sink,
+ byte[] msg, CommsAddrRec addr )
{
boolean allConsumed = true;
boolean[] isLocalP = new boolean[1];
@@ -87,9 +86,9 @@ abstract class XWServiceHelper {
if ( null == sink ) {
sink = getSink( rowid );
}
- if ( GameUtils.feedMessage( context, rowid, msg, addr,
+ if ( GameUtils.feedMessage( mContext, rowid, msg, addr,
sink, bmr, isLocalP ) ) {
- GameUtils.postMoveNotification( context, rowid, bmr,
+ GameUtils.postMoveNotification( mContext, rowid, bmr,
isLocalP[0] );
consumed = true;
}
@@ -119,17 +118,17 @@ abstract class XWServiceHelper {
}
}
- protected boolean handleInvitation( Context context, NetLaunchInfo nli,
+ protected boolean handleInvitation( NetLaunchInfo nli,
String device, DictFetchOwner dfo )
{
boolean success = nli.isValid() && checkNotInFlight( nli );
CurGameInfo gi = null;
if ( success ) {
- long[] rowids = DBUtils.getRowIDsFor( mService, nli.gameID() );
+ long[] rowids = DBUtils.getRowIDsFor( mContext, nli.gameID() );
if ( 0 == rowids.length ) {
// cool: we're good
} else if ( rowids.length < nli.nPlayersT ) {
- success = XWPrefs.getSecondInviteAllowed( mService );
+ success = XWPrefs.getSecondInviteAllowed( mContext );
// Allowing a second game allows the common testing action of
// sending invitation to myself. But we still need to check
@@ -139,12 +138,12 @@ abstract class XWServiceHelper {
try ( GameLock lock = GameLock.tryLockRO( rowid ) ) {
// drop invite if can't open game; likely a dupe!
if ( null != lock ) {
- gi = new CurGameInfo( mService );
+ gi = new CurGameInfo( mContext );
GamePtr gamePtr = GameUtils
- .loadMakeGame( mService, gi, lock );
+ .loadMakeGame( mContext, gi, lock );
gamePtr.release();
} else {
- DbgUtils.toastNoLock( TAG, context, rowid,
+ DbgUtils.toastNoLock( TAG, mContext, rowid,
"handleInvitation()" );
}
}
@@ -164,20 +163,20 @@ abstract class XWServiceHelper {
}
if ( success ) {
- if ( DictLangCache.haveDict( mService, nli.lang, nli.dict ) ) {
- long rowid = GameUtils.makeNewMultiGame( mService, nli,
+ if ( DictLangCache.haveDict( mContext, nli.lang, nli.dict ) ) {
+ long rowid = GameUtils.makeNewMultiGame( mContext, nli,
getSink( 0 ),
getUtilCtxt() );
if ( null != nli.gameName && 0 < nli.gameName.length() ) {
- DBUtils.setName( mService, rowid, nli.gameName );
+ DBUtils.setName( mContext, rowid, nli.gameName );
}
postNotification( device, nli.gameID(), rowid );
} else {
Intent intent = MultiService
- .makeMissingDictIntent( mService, nli, dfo );
- MultiService.postMissingDictNotification( mService, intent,
+ .makeMissingDictIntent( mContext, nli, dfo );
+ MultiService.postMissingDictNotification( mContext, intent,
nli.gameID() );
}
}
@@ -190,7 +189,7 @@ abstract class XWServiceHelper {
protected UtilCtxt getUtilCtxt()
{
if ( null == m_utilCtxt ) {
- m_utilCtxt = new UtilCtxtImpl( mService );
+ m_utilCtxt = new UtilCtxtImpl( mContext );
}
return m_utilCtxt;
}
diff --git a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/jni/CommsAddrRec.java b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/jni/CommsAddrRec.java
index d357bc86b..448253c40 100644
--- a/xwords4/android/app/src/main/java/org/eehouse/android/xw4/jni/CommsAddrRec.java
+++ b/xwords4/android/app/src/main/java/org/eehouse/android/xw4/jni/CommsAddrRec.java
@@ -29,7 +29,7 @@ import org.eehouse.android.xw4.BuildConfig;
import org.eehouse.android.xw4.GameUtils;
import org.eehouse.android.xw4.Log;
import org.eehouse.android.xw4.R;
-import org.eehouse.android.xw4.SMSService;
+import org.eehouse.android.xw4.NBSProto;
import org.eehouse.android.xw4.Utils;
import org.eehouse.android.xw4.WiDirService;
import org.eehouse.android.xw4.WiDirWrapper;
@@ -373,7 +373,7 @@ public class CommsAddrRec {
}
break;
case COMMS_CONN_SMS:
- SMSService.SMSPhoneInfo pi = SMSService.getPhoneInfo( context );
+ NBSProto.SMSPhoneInfo pi = NBSProto.getPhoneInfo( context );
// Do we have phone permission? If not, shouldn't be set at all!
if ( null != pi ) {
sms_phone = pi.number;