Welcome!

Welcome to the official BlackBerry Support Community Forums.

This is your resource to discuss support topics with your peers, and learn from each other.

inside custom component

Java Development

Reply
BlackBerry Development Advisor
Posts: 15,753
Registered: ‎07-09-2008
My Device: BlackBerry PRIV
My Carrier: Bell

Re: Possible bug in OS 5.0 with SendListener?

[ Edited ]

Try wrapping the pushGlobalScreen call as described here:

 

How To - Alert a BlackBerry smartphone user from a Background application
Article Number: DB-00407

http://www.blackberry.com/knowledgecenterpublic/livelink.exe/fetch/2000/348583/800332/800505/800608/...

Mark Sohm
BlackBerry Development Advisor

Please refrain from posting new questions in solved threads.
Problem solved? Click the Accept As Solution button.
Found a bug? Report it using Issue Tracker
Developer
Posts: 19,636
Registered: ‎07-14-2008
My Device: Not Specified

Re: Possible bug in OS 5.0 with SendListener?

Just adding to what Mark says, just becuase you are running in a UiApplicaiton does not mean you have the Event Thread.  So I would change this:

        if ( currentApp instanceof UiApplication )
        {
            // The sendMessage method is being triggered from
            // within a UiApplication.
            // Display the dialog using is show method.
            myDialog.show();
        }

 

to this

 

        if ( currentApp instanceof UiApplication )
        {
            // The sendMessage method is being triggered from
            // within a UiApplication.
            // Display the dialog using is show method.

            currentApp.invokeLater(new Runnable() {

                public void run() {
                    myDialog.show();
                }

            });

        }

 

This is presuming that you get your IllegalStateException on this the dialog.show method.

 

Of course you could still just push a Global Screen regardless.

Developer
Posts: 69
Registered: ‎10-27-2008
My Device: Not Specified

Re: Possible bug in OS 5.0 with SendListener?

Mark/Peter,

 

Finally got (made) the time to try what you guys suggested.  Both of those worked fine, but *ONLY* for dialogs that don't require a return value from the answer given by the user.  This class below demonstrates the issue:

 

 

import java.util.Vector;

import net.rim.blackberry.api.mail.Message;
import net.rim.blackberry.api.mail.SendListener;
import net.rim.blackberry.api.mail.ServiceConfiguration;
import net.rim.blackberry.api.mail.Session;
import net.rim.blackberry.api.mail.Store;
import net.rim.device.api.servicebook.ServiceBook;
import net.rim.device.api.servicebook.ServiceRecord;
import net.rim.device.api.system.Application;
import net.rim.device.api.system.Bitmap;
import net.rim.device.api.ui.Ui;
import net.rim.device.api.ui.UiEngine;
import net.rim.device.api.ui.component.Dialog;

public class SendListener5_0TestApp extends Application implements SendListener
{
    public static void main( String[] args )
    {
        SendListener5_0TestApp theApp = new SendListener5_0TestApp();
        theApp.enterEventDispatcher();
    }

    public SendListener5_0TestApp()
    {
        // Add the listener for encrypting outgoing messages,
        // one for each mail instance in the service book
        ServiceRecord[] records = ServiceBook.getSB().getRecords();
        if ( records != null )
        {
            Vector addedAccounts = new Vector();
            for ( int i = 0; i < records.length; i++ )
            {
                try
                {
                    ServiceRecord currentRecord = records[ i ];
                    if ( currentRecord != null
                         && currentRecord.getCid().equalsIgnoreCase( "CMIME" ) )
                    {
                        ServiceConfiguration currentConfiguration = new ServiceConfiguration(
                                                                                              currentRecord );
                        if ( !addedAccounts.contains( currentConfiguration
                            .getName() ) )
                        {
                            Store currentStore = Session
                                .getInstance( currentConfiguration ).getStore();
                            currentStore.addSendListener( this );

                            addedAccounts.addElement( currentConfiguration
                                .getName() );
                        }
                    }
                }
                catch ( Exception e )
                {
                    // Ignore it and try the next one
                }
            }
        }
    }

    public boolean sendMessage( Message msg )
    {
        // ###
        int dialogResponse = displayDialog();
        // ###

        if ( dialogResponse == 0 )
        {
            return true;
        }
        return false;

    }

    private int displayDialog()
    {
        Object[] choices = new Object[] { "Yes", "No" };
        final Dialog dialog = new Dialog(
                                          "Would you like to send the message?",
                                          choices,
                                          null,
                                          0,
                                          Bitmap
                                              .getPredefinedBitmap( Bitmap.QUESTION ) )
        {
            // Override inHolster to prevent the Dialog from being dismissed
            // when a user holsters their BlackBerry. This can
            // cause a deadlock situation as the Messages
            // application tries to save a draft of the message
            // while the SendListener is waiting for the user to
            // dismiss the Dialog.
            public void inHolster()
            {
            }
        };

        // Obtain the application triggering the SendListener.
        Application.getApplication().invokeAndWait( new Runnable()
        {
            public void run()
            {
                // The sendMessage method is being triggered from
                // within an application (background application).
                synchronized ( Application.getEventLock() )
                {
                    Ui.getUiEngine().pushGlobalScreen( dialog,
                                                       0,
                                                       UiEngine.GLOBAL_MODAL );
                }
            }
        } );

        return dialog.getSelectedValue();
    }
}

 

The issue is that OS 5.0 is freezing during the synchronized block in the Runnable.  If I remove the synchronization, the device will display an error (IllegalStateException), and continue on, but won't wait for the result for the SendListener to make a decision with.

 

I'm leaning towards it being an OS 5.0 bug, in that there is something that has been added to the OS that's grabbing the lock during a SendListener's execution, preventing my SendListener from being able to grab the lock.  Is there a workaround?  Is there another way to accomplish what the 'sendMessage' method is trying to do with the displayDialog method?

 

Matty

 

 

Highlighted
Developer
Posts: 19,636
Registered: ‎07-14-2008
My Device: Not Specified

Re: Possible bug in OS 5.0 with SendListener?

Sorry, only had a quick look, but there are some confusing aspects to this code:

 

        Application.getApplication().invokeAndWait( new Runnable()
        {
            public void run()
            {
                // The sendMessage method is being triggered from
                // within an application (background application).
                synchronized ( Application.getEventLock() )
                {
                    Ui.getUiEngine().pushGlobalScreen( dialog,
                                                       0,
                                                       UiEngine.GLOBAL_MODAL );
                }
            }
        } );

 

The point of using Application.getApplication().invokeAndWait is to get your Runnable executing on the Event Thread and wait for it.  If an Application has done an 'enterDisplatchThread' then it will have an Event Thread, and so can use this Thread to schedule processing that need to be run sequentially for example,  For UiApplications it is usually used to schedule UI updates, because in this case, the Event Thread also always runs with the Event Lock, and so Ui updates are synchronized on that.  So with in the Runnable, you do not need to get the Event Lock.  However your code does attempt to get it  So I think you either need to use the invokeAndWait or the synchronize, but not both.

 

Also you might find there are differences between the OS's in regards as the status of the invoking Application (could be Background Application, could be UiApplication) and whether the listener is called with the Event Thread.  I think these will determine the appropriate way to ask your user the question you want to, and get a response.  So can you, for OS 5.0 and non OS 5.0, tell us whether this code is invoked with the Event Thread or not and from a UiApplication or not?

Developer
Posts: 69
Registered: ‎10-27-2008
My Device: Not Specified

Re: Possible bug in OS 5.0 with SendListener?

Peter,

 

That helped, actually, but didn't solve anything.  Smiley Happy

 

I put some logging into the test application and OS 4.7 ran perfectly -- it showed the event thread being used in the invokeAndWait method, as well as it being a UiApplication.  However, in 5.0, the run() method isn't even getting fired off -- the deadlock seems to be before the Runnable is even created.  I had figured it was a deadlock with the synchronized block, but it seems to not even be going into the run() method at all!

 

Any ideas on why that would be?  5.0 behaves normally (according to the logging) up until the invokeAndWait() call, then the OS freezes.

 

 

Matty

 

Developer
Posts: 19,636
Registered: ‎07-14-2008
My Device: Not Specified

Re: Possible bug in OS 5.0 with SendListener?

I don't have the answer here, I'm just trying to tie it down a little.  I think I'm gong to have to try to replicate this.  Don't have time this afternoon, perhaps later.

 

But are you testing on device or Simulator?  Please say Simulator or I can't help....

Developer
Posts: 69
Registered: ‎10-27-2008
My Device: Not Specified

Re: Possible bug in OS 5.0 with SendListener?

Yeah, OS 5.0 simulators (I'm using a 9700 at 5.0.0.228 and 9500 at 5.0.0.252).  This type of code block has worked on every simulator and device for OS 4.1 to 4.7, so anything will work (I use 8900 and 9000 for regression, but others have been tried and work).

 

 

Thanks

Matty

Developer
Posts: 19,636
Registered: ‎07-14-2008
My Device: Not Specified

Re: Possible bug in OS 5.0 with SendListener?

I have played with this and I believe, recreated your bug.

 

I have also noted this new Thread,

http://supportforums.blackberry.com/t5/Java-Development/Concurency-and-thread-problem-while-working-...

 

which looks a similar problem.

 

I'm beginning to think this is an OS 5.0 bug (or undocumented change that needs code to work around).  I would report this on the Issue Tracker.

Developer
Posts: 69
Registered: ‎10-27-2008
My Device: Not Specified

Re: Possible bug in OS 5.0 with SendListener?

Peter,

 

Thanks for testing it out.  With the post you referred to, I'm beginning to think that it's possibly a thread pool issue, where the new thread can't get fired because the pool is fully being used.  The issue jivkoto mentions is on an older OS (at least, as he says he's seen the issue on a 8310), whereas my problem is only on OS 5.0 and higher -- however, he is *manually* adding more threads, which may be capping the OS native thread pool earlier.  Just a gut feeling, without knowing the specifics of how the OS is set up.

 

 

Matty

 

Developer
Posts: 19,636
Registered: ‎07-14-2008
My Device: Not Specified

Re: Possible bug in OS 5.0 with SendListener?

Apologies, misread the post I referenced, I thought he was testing on OS 5.0 ike you.  Ignore that comment then....