[android-developers] Re: RemoteCallbackList.getBroadcastItem(int) sometimes returns null

2009-03-13 Thread Dianne Hackborn
On Thu, Mar 12, 2009 at 8:08 PM, Streets Of Boston
flyingdutc...@gmail.comwrote:

 I thought that beginBroadcast() would lock the callback-list for
 modification and finishBroadcast() would unlock it again. This way, N
 should always be the number of items in this HashMap you were
 mentioning. Am i correct in this.


No, it only locks internally in beginBroadcast() to create the list.  If you
may have multiple threads calling beginBroadcast(), they need to do their
own synchronization, holding your own lock from before calling
beginBroadcast() to after finishBroadcast().

-- 
Dianne Hackborn
Android framework engineer
hack...@android.com

Note: please don't send private questions to me, as I don't have time to
provide private support.  All such questions should be posted on public
forums, where I and others can see and answer them.

--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google
Groups Android Developers group.
To post to this group, send email to android-developers@googlegroups.com
To unsubscribe from this group, send email to
android-developers-unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/android-developers?hl=en
-~--~~~~--~~--~--~---



[android-developers] Re: RemoteCallbackList.getBroadcastItem(int) sometimes returns null

2009-03-13 Thread Streets Of Boston

Ah, thanks.

Either way, it means that the number of items in the list accessed by
getBroadcastItem is always equal to N.
The problem remains: How can getBroadcastItem(int) return null?

On Mar 13, 4:53 am, Dianne Hackborn hack...@android.com wrote:
 On Thu, Mar 12, 2009 at 8:08 PM, Streets Of Boston
 flyingdutc...@gmail.comwrote:

  I thought that beginBroadcast() would lock the callback-list for
  modification and finishBroadcast() would unlock it again. This way, N
  should always be the number of items in this HashMap you were
  mentioning. Am i correct in this.

 No, it only locks internally in beginBroadcast() to create the list.  If you
 may have multiple threads calling beginBroadcast(), they need to do their
 own synchronization, holding your own lock from before calling
 beginBroadcast() to after finishBroadcast().

 --
 Dianne Hackborn
 Android framework engineer
 hack...@android.com

 Note: please don't send private questions to me, as I don't have time to
 provide private support.  All such questions should be posted on public
 forums, where I and others can see and answer them.
--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google
Groups Android Developers group.
To post to this group, send email to android-developers@googlegroups.com
To unsubscribe from this group, send email to
android-developers-unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/android-developers?hl=en
-~--~~~~--~~--~--~---



[android-developers] Re: RemoteCallbackList.getBroadcastItem(int) sometimes returns null

2009-03-13 Thread Dianne Hackborn
On Fri, Mar 13, 2009 at 7:27 AM, Streets Of Boston
flyingdutc...@gmail.comwrote:

 Either way, it means that the number of items in the list accessed by
 getBroadcastItem is always equal to N.
 The problem remains: How can getBroadcastItem(int) return null?


I'm not sure what you mean by either way -- if you are doing this from
multiple threads, your threads can clobber the list, which can lead to this
kind of problem.

-- 
Dianne Hackborn
Android framework engineer
hack...@android.com

Note: please don't send private questions to me, as I don't have time to
provide private support.  All such questions should be posted on public
forums, where I and others can see and answer them.

--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google
Groups Android Developers group.
To post to this group, send email to android-developers@googlegroups.com
To unsubscribe from this group, send email to
android-developers-unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/android-developers?hl=en
-~--~~~~--~~--~--~---



[android-developers] Re: RemoteCallbackList.getBroadcastItem(int) sometimes returns null

2009-03-13 Thread Streets Of Boston

Ah, now i get it! :-)

Indeed, sendProgressCallback can be called from multiple threads. And
with your earlier explanation that the beginBroadcast does not do
locking (only a brief internal lock), it may explain the problem. In
other words, RemoteCallbackList is not thread-safe across multiple
calls to it.

I should put the broadcast code inside a 'synchronized(mCallbacks)
{ ... }' block or surround it with a ReentrantLock.
Or create mCallbacks instances for each possible thread and have my
listeners register with each of them.

Thank you very much for your help.
Have a great weekend!

On Mar 13, 12:58 pm, Dianne Hackborn hack...@android.com wrote:
 On Fri, Mar 13, 2009 at 7:27 AM, Streets Of Boston
 flyingdutc...@gmail.comwrote:

  Either way, it means that the number of items in the list accessed by
  getBroadcastItem is always equal to N.
  The problem remains: How can getBroadcastItem(int) return null?

 I'm not sure what you mean by either way -- if you are doing this from
 multiple threads, your threads can clobber the list, which can lead to this
 kind of problem.

 --
 Dianne Hackborn
 Android framework engineer
 hack...@android.com

 Note: please don't send private questions to me, as I don't have time to
 provide private support.  All such questions should be posted on public
 forums, where I and others can see and answer them.
--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google
Groups Android Developers group.
To post to this group, send email to android-developers@googlegroups.com
To unsubscribe from this group, send email to
android-developers-unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/android-developers?hl=en
-~--~~~~--~~--~--~---



[android-developers] Re: RemoteCallbackList.getBroadcastItem(int) sometimes returns null

2009-03-13 Thread Dianne Hackborn
If your callbacks are oneway, the easiest thing to do is put it all in a big
synchronized() block.  Be aware though that if the callback is into the
local process, it will still be synchronous, so holding a lock while doing
this can be a problem.

Usually the safest thing is to have a handler that you post a message to,
which does the callbacks.  Then you don't need any locking since the
broadcasts are serialized by the handler.

On Fri, Mar 13, 2009 at 10:55 AM, Streets Of Boston flyingdutc...@gmail.com
 wrote:


 Ah, now i get it! :-)

 Indeed, sendProgressCallback can be called from multiple threads. And
 with your earlier explanation that the beginBroadcast does not do
 locking (only a brief internal lock), it may explain the problem. In
 other words, RemoteCallbackList is not thread-safe across multiple
 calls to it.

 I should put the broadcast code inside a 'synchronized(mCallbacks)
 { ... }' block or surround it with a ReentrantLock.
 Or create mCallbacks instances for each possible thread and have my
 listeners register with each of them.

 Thank you very much for your help.
 Have a great weekend!

 On Mar 13, 12:58 pm, Dianne Hackborn hack...@android.com wrote:
  On Fri, Mar 13, 2009 at 7:27 AM, Streets Of Boston
  flyingdutc...@gmail.comwrote:
 
   Either way, it means that the number of items in the list accessed by
   getBroadcastItem is always equal to N.
   The problem remains: How can getBroadcastItem(int) return null?
 
  I'm not sure what you mean by either way -- if you are doing this from
  multiple threads, your threads can clobber the list, which can lead to
 this
  kind of problem.
 
  --
  Dianne Hackborn
  Android framework engineer
  hack...@android.com
 
  Note: please don't send private questions to me, as I don't have time to
  provide private support.  All such questions should be posted on public
  forums, where I and others can see and answer them.
 



-- 
Dianne Hackborn
Android framework engineer
hack...@android.com

Note: please don't send private questions to me, as I don't have time to
provide private support.  All such questions should be posted on public
forums, where I and others can see and answer them.

--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google
Groups Android Developers group.
To post to this group, send email to android-developers@googlegroups.com
To unsubscribe from this group, send email to
android-developers-unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/android-developers?hl=en
-~--~~~~--~~--~--~---



[android-developers] Re: RemoteCallbackList.getBroadcastItem(int) sometimes returns null

2009-03-13 Thread Streets Of Boston

Alas, this one is not a one-way interface. It expects a boolean back:
False = cancel upload of image, True = continue uploading image. It
allows the (remote) client to cancel uploads forcefully. Luckily, the
client receiving the call-back can return this answer really fast.

The client is not the same process. It is a different app (Activity)
in a different process.

What is your opinion, in terms of speed/performance: One 'mCallbacks'
instance for the Service, sending this callback to its clients, inside
a synchronized(...) block or having each a 'mCallbacks' for each
thread (max 3)? Which one would be better?
The client is always remote (other process).

Thanks!
On Mar 13, 2:29 pm, Dianne Hackborn hack...@android.com wrote:
 If your callbacks are oneway, the easiest thing to do is put it all in a big
 synchronized() block.  Be aware though that if the callback is into the
 local process, it will still be synchronous, so holding a lock while doing
 this can be a problem.

 Usually the safest thing is to have a handler that you post a message to,
 which does the callbacks.  Then you don't need any locking since the
 broadcasts are serialized by the handler.

 On Fri, Mar 13, 2009 at 10:55 AM, Streets Of Boston flyingdutc...@gmail.com





  wrote:

  Ah, now i get it! :-)

  Indeed, sendProgressCallback can be called from multiple threads. And
  with your earlier explanation that the beginBroadcast does not do
  locking (only a brief internal lock), it may explain the problem. In
  other words, RemoteCallbackList is not thread-safe across multiple
  calls to it.

  I should put the broadcast code inside a 'synchronized(mCallbacks)
  { ... }' block or surround it with a ReentrantLock.
  Or create mCallbacks instances for each possible thread and have my
  listeners register with each of them.

  Thank you very much for your help.
  Have a great weekend!

  On Mar 13, 12:58 pm, Dianne Hackborn hack...@android.com wrote:
   On Fri, Mar 13, 2009 at 7:27 AM, Streets Of Boston
   flyingdutc...@gmail.comwrote:

Either way, it means that the number of items in the list accessed by
getBroadcastItem is always equal to N.
The problem remains: How can getBroadcastItem(int) return null?

   I'm not sure what you mean by either way -- if you are doing this from
   multiple threads, your threads can clobber the list, which can lead to
  this
   kind of problem.

   --
   Dianne Hackborn
   Android framework engineer
   hack...@android.com

   Note: please don't send private questions to me, as I don't have time to
   provide private support.  All such questions should be posted on public
   forums, where I and others can see and answer them.

 --
 Dianne Hackborn
 Android framework engineer
 hack...@android.com

 Note: please don't send private questions to me, as I don't have time to
 provide private support.  All such questions should be posted on public
 forums, where I and others can see and answer them.- Hide quoted text -

 - Show quoted text -
--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google
Groups Android Developers group.
To post to this group, send email to android-developers@googlegroups.com
To unsubscribe from this group, send email to
android-developers-unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/android-developers?hl=en
-~--~~~~--~~--~--~---



[android-developers] Re: RemoteCallbackList.getBroadcastItem(int) sometimes returns null

2009-03-12 Thread Streets Of Boston

m you mean that the value of 'N 'could be larger than the
actual elements accessed by getBroadcastItem(i), i.e. HashMap changes
while looping over the 'N' items...?

For now, i'm check for null and just ignore it. The problem is that it
is very hard to reproduce. It happens on rare occasions, but often
enough to be problematic.

This line has only 3 points in which it could throw a null-pointer
exception (the stack-trace reports the NPE on this line, not inside
progressChanged(...)):
- mCallbacks is null: Not possible. It is declared final and refers to
an instance.
- qiu is null: Not possible. It is a stack-variable and it has been
guarded against null value.
- getBroadcastItem(i): The only one left...

I thought that beginBroadcast() would lock the callback-list for
modification and finishBroadcast() would unlock it again. This way, N
should always be the number of items in this HashMap you were
mentioning. Am i correct in this.

I'll let you know if i can figure out which values for 'i' are
problematic :-)

Thanks for your help.

On Mar 12, 9:27 pm, Dianne Hackborn hack...@android.com wrote:
 Hm actually could you see if it is the -last- ones that are null?  The code
 that makes the list gets a count from the HashMap, and then iterates through
 its values and puts them in the array, and returns the original count.  So
 if that count is different than the number it iterated over, that could be a
 problem.  I'll change it to return the actual number it iterated over, but
 in theory these shouldn't be different.

 On Thu, Mar 12, 2009 at 6:25 PM, Dianne Hackborn hack...@android.comwrote:





  The callbacks are just stored in a HashMap, and the entries there are never
  set null (actually that field is final), so I don't really see how that can
  happen.  Are you sure you aren't potentially doing this loop from different
  threads without doing your own synchronization?

  On Thu, Mar 12, 2009 at 6:07 PM, Streets Of Boston 
  flyingdutc...@gmail.com wrote:

  Hi,

  I found out that RemoteCallbackList.getBroadcastItem(int) sometimes
  returns null.  I have this code in my Service and it raises a null-
  pointer exception:

  ...
     // instance variable of my Service
     final RemoteCallbackListIProgressCallback mCallbacks
             = new RemoteCallbackListIProgressCallback();

  ...
  ...
  public boolean sendProgressCallback(String imgUri, int albumId, int
  progressBytes, int progressPercent) {
         final QueuedImageUpload qiu = getUploadingImage(imgUri, albumId);
         if (qiu == null)
             return true;

         qiu.setSizeUploaded(progressBytes);

         final int totalSizePercent =
  mQueues.calculateRemainingSizePercent();
         final int N = mCallbacks.beginBroadcast();
         try {
                 for (int i = 0; i  N; i++) {
                         try {
                                 if
  (!mCallbacks.getBroadcastItem(i).progressChanged(qiu.getID(),
  imgUri, albumId, progressPercent, totalSizePercent)) {
                                         return false;
                                 }
                         } catch (RemoteException e) {
                                 // The RemoteCallbackList will take care of
  removing
                                 // the dead object for us.
                         }
                 }
         }
         finally {
                 mCallbacks.finishBroadcast();
         }
         return true;
  }

  This line is the one throwing a nullpointer exception:
  if (!mCallbacks.getBroadcastItem(i).progressChanged(qiu.getID(),
  imgUri, albumId, progressPercent, totalSizePercent))

  - The mCallbacks is never null. It is declared as final.
  - The local 'qui' stack-variable is never null. It is guarded by a
  null-pointer check.

  That only leads me to conclude that the call getBroadcastItem(i)
  returns null. However, the documentation states that this method never
  returns null. Is this a bug in Android?

  This problem only happens on occasion (I can not reproduce it
  consistently), but it happens often enough to be of concern for my
  app.

  BTW, someone else reported the same problem a while ago:

 http://groups.google.com/group/android-developers/browse_thread/threa...

  Thank you.
  -- Anton Spaans
 http://soft.antonspaans.com

  --
  Dianne Hackborn
  Android framework engineer
  hack...@android.com

  Note: please don't send private questions to me, as I don't have time to
  provide private support.  All such questions should be posted on public
  forums, where I and others can see and answer them.

 --
 Dianne Hackborn
 Android framework engineer
 hack...@android.com

 Note: please don't send private questions to me, as I don't have time to
 provide private support.  All such questions should be posted on public
 forums, where I and others can see and answer them.- Hide quoted text -

 - Show quoted text -
--~--~-~--~~~---~--~~
You received this message