Bug 674725 - Part Y - Notify when send() fails. r=smaug,cjones sr=sicking

This commit is contained in:
Mounir Lamouri 2011-12-22 23:06:35 +01:00
Родитель f5b00b7840
Коммит c74a4b532f
12 изменённых файлов: 143 добавлений и 9 удалений

Просмотреть файл

@ -68,6 +68,7 @@ EXPORTS_mozilla/dom/sms = \
Types.h \
SmsMessage.h \
SmsRequestManager.h \
SmsRequest.h \
$(NULL)
CPPSRCS = \

Просмотреть файл

@ -192,6 +192,12 @@ SmsRequest::GetError(nsAString& aError)
case eNoError:
SetDOMStringToNull(aError);
break;
case eNoSignalError:
aError.AssignLiteral("NoSignalError");
break;
case eUnknownError:
aError.AssignLiteral("UnknownError");
break;
case eInternalError:
aError.AssignLiteral("InternalError");
break;

Просмотреть файл

@ -53,8 +53,15 @@ class SmsRequest : public nsIDOMMozSmsRequest
public:
friend class SmsRequestManager;
/**
* All SMS related errors that could apply to SmsRequest objects.
* Make sure to keep this list in sync with the list in:
* embedding/android/GeckoSmsManager.java
*/
enum ErrorType {
eNoError = 0,
eNoSignalError,
eUnknownError,
eInternalError,
};

Просмотреть файл

@ -36,7 +36,6 @@
* ***** END LICENSE BLOCK ***** */
#include "SmsRequestManager.h"
#include "SmsRequest.h"
#include "nsIDOMSmsMessage.h"
#include "nsDOMEvent.h"
@ -134,6 +133,22 @@ SmsRequestManager::NotifySmsSent(PRInt32 aRequestId, nsIDOMMozSmsMessage* aMessa
mRequests.ReplaceObjectAt(nsnull, aRequestId);
}
void
SmsRequestManager::NotifySmsSendFailed(PRInt32 aRequestId, SmsRequest::ErrorType aError)
{
NS_ASSERTION(mRequests.Count() > aRequestId && mRequests[aRequestId],
"Got an invalid request id or it has been already deleted!");
// It's safe to use the static_cast here given that we did call
// |new SmsRequest()|.
SmsRequest* request = static_cast<SmsRequest*>(mRequests[aRequestId]);
request->SetError(aError);
DispatchTrustedEventToRequest(ERROR_EVENT_NAME, request);
mRequests.ReplaceObjectAt(nsnull, aRequestId);
}
} // namespace sms
} // namespace dom
} // namespace mozilla

Просмотреть файл

@ -40,6 +40,7 @@
#define mozilla_dom_sms_SmsRequestManager_h
#include "nsCOMArray.h"
#include "SmsRequest.h"
class nsIDOMMozSmsRequest;
class nsPIDOMWindow;
@ -62,6 +63,7 @@ public:
nsIDOMMozSmsRequest** aRequest);
void NotifySmsSent(PRInt32 aRequestId, nsIDOMMozSmsMessage* aMessage);
void NotifySmsSendFailed(PRInt32 aRequestId, SmsRequest::ErrorType aError);
private:
static SmsRequestManager* sInstance;

Просмотреть файл

@ -68,6 +68,9 @@ child:
NotifyRequestSmsSent(SmsMessageData aMessageData, PRInt32 aRequestId,
PRUint64 aProcessId);
NotifyRequestSmsSendFailed(PRInt32 aError, PRInt32 aRequestId,
PRUint64 aProcessId);
parent:
sync HasSupport()
returns (bool aHasSupport);

Просмотреть файл

@ -42,6 +42,7 @@
#include "mozilla/Services.h"
#include "mozilla/dom/ContentChild.h"
#include "SmsRequestManager.h"
#include "SmsRequest.h"
namespace mozilla {
namespace dom {
@ -104,6 +105,21 @@ SmsChild::RecvNotifyRequestSmsSent(const SmsMessageData& aMessage,
return true;
}
bool
SmsChild::RecvNotifyRequestSmsSendFailed(const PRInt32& aError,
const PRInt32& aRequestId,
const PRUint64& aProcessId)
{
if (ContentChild::GetSingleton()->GetID() != aProcessId) {
return true;
}
SmsRequestManager::GetInstance()->NotifySmsSendFailed(aRequestId,
SmsRequest::ErrorType(aError));
return true;
}
} // namespace sms
} // namespace dom
} // namespace mozilla

Просмотреть файл

@ -51,6 +51,7 @@ public:
NS_OVERRIDE virtual bool RecvNotifySentMessage(const SmsMessageData& aMessage);
NS_OVERRIDE virtual bool RecvNotifyDeliveredMessage(const SmsMessageData& aMessage);
NS_OVERRIDE virtual bool RecvNotifyRequestSmsSent(const SmsMessageData& aMessage, const PRInt32& aRequestId, const PRUint64& aProcessId);
NS_OVERRIDE virtual bool RecvNotifyRequestSmsSendFailed(const PRInt32& aError, const PRInt32& aRequestId, const PRUint64& aProcessId);
};
} // namespace sms

Просмотреть файл

@ -125,6 +125,7 @@ public class GeckoAppShell
public static native int saveMessageInSentbox(String aReceiver, String aBody, long aTimestamp);
public static native void notifySmsSent(int aId, String aReceiver, String aBody, long aTimestamp, int aRequestId, long aProcessId);
public static native void notifySmsDelivered(int aId, String aReceiver, String aBody, long aTimestamp);
public static native void notifySmsSendFailed(int aError, int aRequestId, long aProcessId);
// A looper thread, accessed by GeckoAppShell.getHandler
private static class LooperThread extends Thread {

Просмотреть файл

@ -98,10 +98,16 @@ class Envelope
*/
protected boolean[] mFailing;
/**
* Error type (only for sent).
*/
protected int mError;
public Envelope(int aId, int aParts) {
mId = aId;
mMessageId = -1;
mMessageTimestamp = 0;
mError = GeckoSmsManager.kNoError;
int size = Envelope.SubParts.values().length;
mRemainingParts = new int[size];
@ -149,6 +155,14 @@ class Envelope
public void setMessageTimestamp(long aMessageTimestamp) {
mMessageTimestamp = aMessageTimestamp;
}
public int getError() {
return mError;
}
public void setError(int aError) {
mError = aError;
}
}
/**
@ -221,6 +235,15 @@ public class GeckoSmsManager
private final static int kMaxMessageSize = 160;
/*
* Keep the following error codes in sync with |ErrorType| in:
* dom/sms/src/SmsRequest.h
*/
public final static int kNoError = 0;
public final static int kNoSignalError = 1;
public final static int kUnknownError = 2;
public final static int kInternalError = 3;
@Override
public void onReceive(Context context, Intent intent) {
if (intent.getAction().equals(ACTION_SMS_RECEIVED)) {
@ -276,9 +299,21 @@ public class GeckoSmsManager
if (getResultCode() != Activity.RESULT_OK) {
// TODO: manage error types.
Log.i("GeckoSmsManager", "SMS part sending failed!");
switch (getResultCode()) {
case SmsManager.RESULT_ERROR_NULL_PDU:
envelope.setError(kInternalError);
break;
case SmsManager.RESULT_ERROR_NO_SERVICE:
case SmsManager.RESULT_ERROR_RADIO_OFF:
envelope.setError(kNoSignalError);
break;
case SmsManager.RESULT_ERROR_GENERIC_FAILURE:
default:
envelope.setError(kUnknownError);
break;
}
envelope.markAsFailed(part);
Log.i("GeckoSmsManager", "SMS part sending failed!");
}
if (envelope.arePartsRemaining(part)) {
@ -287,7 +322,9 @@ public class GeckoSmsManager
if (envelope.isFailing(part)) {
if (part == Envelope.SubParts.SENT_PART) {
// TODO: inform about the send failure.
GeckoAppShell.notifySmsSendFailed(envelope.getError(),
bundle.getInt("requestId"),
bundle.getLong("processId"));
Log.i("GeckoSmsManager", "SMS sending failed!");
} else {
// It seems unlikely to get a result code for a failure to deliver.
@ -334,11 +371,6 @@ public class GeckoSmsManager
}
public static void send(String aNumber, String aMessage, int aRequestId, long aProcessId) {
/*
* TODO:
* This is a basic send method that doesn't handle errors and doesn't listen to
* delivered messages.
*/
int envelopeId = Postman.kUnknownEnvelopeId;
try {
@ -419,6 +451,8 @@ public class GeckoSmsManager
if (envelopeId != Postman.kUnknownEnvelopeId) {
Postman.getInstance().destroyEnvelope(envelopeId);
}
GeckoAppShell.notifySmsSendFailed(kUnknownError, aRequestId, aProcessId);
}
}

Просмотреть файл

@ -255,6 +255,7 @@ SHELL_WRAPPER0_WITH_RETURN(testDirectTexture, bool);
SHELL_WRAPPER3_WITH_RETURN(saveMessageInSentbox, jint, jstring, jstring, jlong);
SHELL_WRAPPER6(notifySmsSent, jint, jstring, jstring, jlong, jint, jlong);
SHELL_WRAPPER4(notifySmsDelivered, jint, jstring, jstring, jlong);
SHELL_WRAPPER3(notifySmsSendFailed, jint, jint, jlong);
static void * xul_handle = NULL;
static time_t apk_mtime = 0;
@ -645,6 +646,7 @@ loadLibs(const char *apkName)
GETFUNC(saveMessageInSentbox);
GETFUNC(notifySmsSent);
GETFUNC(notifySmsDelivered);
GETFUNC(notifySmsSendFailed);
#undef GETFUNC
sStartupTimeline = (uint64_t *)__wrap_dlsym(xul_handle, "_ZN7mozilla15StartupTimeline16sStartupTimelineE");
gettimeofday(&t1, 0);

Просмотреть файл

@ -66,6 +66,7 @@
#include "mozilla/dom/sms/Types.h"
#include "mozilla/dom/sms/PSms.h"
#include "mozilla/dom/sms/SmsRequestManager.h"
#include "mozilla/dom/sms/SmsRequest.h"
#include "mozilla/dom/sms/SmsParent.h"
#include "nsISmsDatabaseService.h"
@ -93,6 +94,7 @@ extern "C" {
NS_EXPORT PRInt32 JNICALL Java_org_mozilla_gecko_GeckoAppShell_saveMessageInSentbox(JNIEnv* jenv, jclass, jstring, jstring, jlong);
NS_EXPORT void JNICALL Java_org_mozilla_gecko_GeckoAppShell_notifySmsSent(JNIEnv* jenv, jclass, jint, jstring, jstring, jlong, jint, jlong);
NS_EXPORT void JNICALL Java_org_mozilla_gecko_GeckoAppShell_notifySmsDelivered(JNIEnv* jenv, jclass, jint, jstring, jstring, jlong);
NS_EXPORT void JNICALL Java_org_mozilla_gecko_GeckoAppShell_notifySmsSendFailed(JNIEnv* jenv, jclass, jint, jint, jlong);
#ifdef MOZ_JAVA_COMPOSITOR
NS_EXPORT void JNICALL Java_org_mozilla_gecko_GeckoAppShell_bindWidgetTexture(JNIEnv* jenv, jclass);
@ -400,6 +402,50 @@ Java_org_mozilla_gecko_GeckoAppShell_notifySmsDelivered(JNIEnv* jenv, jclass,
NS_DispatchToMainThread(runnable);
}
NS_EXPORT void JNICALL
Java_org_mozilla_gecko_GeckoAppShell_notifySmsSendFailed(JNIEnv* jenv, jclass,
jint aError,
jint aRequestId,
jlong aProcessId)
{
class NotifySmsSendFailedRunnable : public nsRunnable {
public:
NotifySmsSendFailedRunnable(SmsRequest::ErrorType aError,
PRInt32 aRequestId, PRUint64 aProcessId)
: mError(aError)
, mRequestId(aRequestId)
, mProcessId(aProcessId)
{}
NS_IMETHODIMP Run() {
if (mProcessId == 0) { // Parent process.
SmsRequestManager::GetInstance()->NotifySmsSendFailed(mRequestId, mError);
} else { // Content process.
nsTArray<SmsParent*> spList;
SmsParent::GetAll(spList);
for (PRUint32 i=0; i<spList.Length(); ++i) {
unused << spList[i]->SendNotifyRequestSmsSendFailed(mError,
mRequestId,
mProcessId);
}
}
return NS_OK;
}
private:
SmsRequest::ErrorType mError;
PRInt32 mRequestId;
PRUint64 mProcessId;
};
nsCOMPtr<nsIRunnable> runnable =
new NotifySmsSendFailedRunnable(SmsRequest::ErrorType(aError), aRequestId, aProcessId);
NS_DispatchToMainThread(runnable);
}
#ifdef MOZ_JAVA_COMPOSITOR
NS_EXPORT void JNICALL