08-19-2010 09:31 AM - edited 08-19-2010 09:33 AM
Greetings!
Not sure what kind of problem I facing, but still quite interesting.
I have an UiApplication which start a thread to listen for incoming SMS and automatically answer them. This same class implements PhoneListener as bellow:
public class SMSSenderReceiver extends Thread implements PhoneListener {
private static DatagramConnection _dc;
private static int _callIdIncoming;
private static int _callIdAnswered;
public static String _phoneNumber;
static {
try {
_dc = (DatagramConnection) Connector.open("sms://");
} catch (IOException e) {
System.out.println(e);
}
}
public SMSSenderReceiver() {
super();
_callIdIncoming = -1;
_callIdAnswered = -1;
Phone.addPhoneListener(this);
}
public void run() {
try {
for (;;) {
Datagram d = _dc.newDatagram(_dc.getMaximumLength());
_dc.receive(d);
String address = d.getAddress();
if (address.startsWith("//")) {
address = address.substring(2);
}
String answer = getResponseByPhone(address);
if (answer != null) {
answer.getBytes();
Datagram returnpacket = _dc.newDatagram(_dc
.getMaximumLength());
returnpacket.setAddress(d.getAddress());
returnpacket.setData(answer.getBytes(), 0, answer.length());
_dc.send(returnpacket);
}
}
} catch (IOException ioe) {
System.out.println(ioe);
Phone.removePhoneListener(this);
}
}
private static String getResponseByPhone(final String phone) {
TextResponses tr = TextResponses.getInstance();
MultiMap mm = tr.getResponses();
Enumeration valuesEnum = mm.keys();
while (valuesEnum.hasMoreElements()) {
String element = valuesEnum.nextElement().toString();
if (mm.containsValue(element, phone)) {
return element;
} else {
continue;
}
}
return null;
}
// public void missedCallSMSSender(final String address) {
// try {
// if(_callIdAnswered != _callIdIncoming){
// // if (address.startsWith("//")) {
// // address = address.substring(2);
// // }
// String answer = this.getResponseByPhone(address);
// if (answer != null) {
// answer.getBytes();
// Datagram returnpacket = _dc.newDatagram(_dc
// .getMaximumLength());
// returnpacket.setAddress("//" + address);
// returnpacket.setData(answer.getBytes(), 0, answer
// .length());
// _dc.send(returnpacket);
// }
// _callIdAnswered = _callIdIncoming = -1;
// //_phoneCallsHash.remove("" + _callIdIncoming);
// }
// } catch (Exception e) {
// System.out.println(e);
// }
// }
public void callIncoming(final int callId) {
if(_callIdIncoming != callId){
UiApplication.getUiApplication().invokeLater(new Runnable(){
public void run() {
_callIdIncoming = callId;
PhoneCall phoneCall = Phone.getCall( callId );
_phoneNumber = null;
try {
_phoneNumber = phoneCall.getDisplayPhoneNumber();
String tempNumber = null;
for(int i = _phoneNumber.length() -1 ;i >= 0; --i) {
if(Character.isDigit(_phoneNumber.charAt(i))){
tempNumber = _phoneNumber.charAt(i) + ((tempNumber == null) ? "" : tempNumber) ;
}
}
_phoneNumber = tempNumber;
System.out.println("**bleep** Phone Number: " + _phoneNumber);
} catch(NullPointerException npe) {
_phoneNumber = "0";
System.out.println("NULL!!!!" + npe);
}
}
});
}
}
public void callAnswered(int callId) {
_callIdAnswered = callId;
}
public void callDisconnected(int callId) {
UiApplication.getUiApplication().invokeLater(new Runnable(){
public void run() {
//System.out.println("**bleep** Phone Number: " + _phoneNumber);
//SMSSenderReceiver.this.missedCallSMSSender(_phon eNumber);
String address = _phoneNumber;
if(_callIdAnswered != _callIdIncoming){
// if (address.startsWith("//")) {
// address = address.substring(2);
// }
String answer = getResponseByPhone(address);
if (answer != null) {
answer.getBytes();
try {
Datagram returnpacket = _dc.newDatagram(_dc.getMaximumLength());
returnpacket.setAddress("//" + address);
returnpacket.setData(answer.getBytes(), 0, answer
.length());
_dc.send(returnpacket);
} catch(Exception e) {
System.out.println(e);
}
}
_callIdAnswered = _callIdIncoming = -1;
}
}
});
}
...
The goal is to send a SMS for each missed call. So, on incomingCall I catch the call Id and the phone number assign them to the static variables. If the call is answered I catch the call id also. Once the the call is disconnected I just check the call answered id and incoming id in case they differ from each other I got a miss call and I have to send a SMS.
The problem is once the callDisconneted is called I no longer have the _phoneNumber value. On incomingCall I able to see the number, but not after all. Why? Seems to be a basic fundamental about multi-thread.
Does anybody know what is happening?
Thanks in advance!
--
Solved! Go to Solution.
08-19-2010 10:08 AM - edited 08-19-2010 10:09 AM
This issue probably has to do with the fact that the call listener is actually coming into your code on the phone application thread. Each application gets a separate copy of static context. Consequently, you will not see the same data when you access this variable in your own application process.
You probably have two choices here: (a) send yourself a global event form the call listener, then pick up this event in your own process, or (b) use the runtime store to retain the value so that both processes can *see* it.