BREW Debug Sequences
BREW offers a number of debug modes to assist in diagnosing BREW application errors. These modes are activated at any time while BREW is active -- including within the BREW applications manager -- by entering specific key sequences. This document describes the supported BREW debug modes and how to activate them within BREW.
Activating BREW debug sequences
The process for enabling BREW debug modes depends on the BREW version used, but as a general rule involves entering a sequence of OEM-configurable keys followed by a debug mode number (defined later in this document), and a terminator key in 3.x devices. The default sequence for enabling debug modes is three ‘#’ keys; however, the prefix key and prefix length are OEM configurable, meaning this sequence may vary from device to device. The examples in this document assume the default debug mode sequence. More than one debug mode may be active simultaneously. BREW saves the active debug modes when the phone is shut down (only when shut down properly, not as a result of a crash), so the active debug modes will continue to stay active after power-cycle until explicitly disabled.
BREW 2.0 and earlier: the debug sequences are enabled by default, regardless of whether the phone has been test-enabled. To activate the debug sequence, enter ###[debug mode].
BREW 2.1, 3.0: debug sequences are enabled only if the phone is in test-enabled state. To activate the debug sequence, enter ###[debug mode].
BREW 3.1+: devices must be put in a debug key mode before debug key sequences are recognized by BREW. Once in debug key mode, the debug sequences look very much like they did in previous BREW releases. This change was required to reduce the likelihood of accidental debug mode activation, since test enabling was removed from BREW in 3.1. In most cases the length of the new debug key mode sequence will eliminate the need for the OEM to make changes to the default BREW debug mode sequences.
To put a BREW 3.1 device in debug key mode, enter a key sequence consisting of the following three parts:
- an OEM-configured prefix (three ‘#’ keys by default)
- spelling out BREWDEBUG (273933284)
- a terminator key (‘#’ in the example below, but any key except 0-9 can be used)
For example, ###BREWDEBUG# (###273933284#) would turn on the debug key mode if entered on a device with ### as the OEM-configured prefix.
Once in debug key mode, turn on BREW debug features by entering the following three-part sequence:
- the OEM-configured prefix
- the decimal number of the BREW debugging
- a terminator key (should be the same key used as the terminator in the sequence to turn on debug mode)
This is similar to previous BREW versions with the addition of the terminator key: ###[debug mode]#
To turn off debug key mode, simply type the prefix and the terminator without any numbers. In this example, #### leaves debug key mode. Leaving this mode does not reset any of the above debug modes, it merely disables special handling of any further ###-prefixed key sequences.
Supported debug modes
Debug modes supported vary by BREW version. The number listed corresponds to the number entered as debug mode in the examples above.
Debug reset (Debug number 0 on all BREW versions)
Turns all currently activated debug modes off.
Memory validation (Debug number 1 on all BREW versions)
Turns on enhanced pointer validation across many BREW APIs, particularly AEEStdLib functions. When this mode is enabled, BREW will perform additional checks on pointers to ensure they point to a valid block of memory in the heap that is large enough to support the intended operation.
Consider the following code:
char *psz1, *psz2="test"; STRCMP(psz1, psz2);
Clearly this is incorrect as psz1 has not been assigned. Results may vary across devices when memory validation mode is not active, but generally the device will crash and power-cycle. If memory validation mode is active, BREW will throw an exception when the error occurs. This exception causes BREW to display a diagnostic screen for several seconds indicating the type of exception (memory access error, memory corruption, or stack overflow). When running on the Simulator, BREW will also display additional information about the operation that caused the error (for example the name of the API method that was called).
Network debugging (Debug number 2 on all BREW versions)
When network debugging mode is enabled, BREW will print out expanded networking messages (including the packet contents) through DBGPRINTF(). BREW also displays a character corresponding to the current network state on the device in the upper-right corner of the display. The characters and associated network states are as follows:
|BREW 2.0 and higher:|
Available memory (Debug number 3 on all BREW versions)
BREW draws the free memory (retrieved through the GETRAMFREE() helper function) in a box on the upper-left corner of the screen. Note that this is the total free memory, not necessarily the size of the largest free block that can be allocated. In cases where the heap has become fragmented, the free memory will not be in a single contiguous block.
Synchronous DBGPRINTF (Debug number 4 on BREW 3.1.0+, debug number 7 before 3.1.0)
This debug sequence toggles between two modes: synchronous DBGPRINTF() and asynchronous DBGFPRINTF(). In synchronous DBGPRINTF mode, BREW waits for a certain duration (100 ms in BREW 3.1.0+, 200 ms before 3.1.0) before returning from a DBGPRINTF() statement in order to allow time for the DBGPRINTF() message to be sent on the serial port. In the default, asynchronous mode, the DBGPRINTF() returns immediately after the message is sent. When synchronous DBGPRINTF mode is active, there will be a noticeable impact on BREW performance. Typically this is useful when attempting to diagnose a crash to ensure that BREW has enough time to send the debug message before crashing.
Dump modules (Debug number 5 on BREW 3.1.0+, debug number 8 on BREW 2.1.3-3.0)
When this mode is triggered, BREW will dump information about all installed BREW modules via DBGPRINTF(). This information will look something like the following (numbers in parentheses added to log messages for clarity):
*AEEModule.c:586 – (1)fs:/mif/helloworld.mif (2)Item: 4294967045 (3)Pkg: 0 (4)(DYN)
(1) File path and name of the MIF corresponding to this module
(2) Item ID stored in the MIF tail. Only valid for OTA installs or preinstalled dynamic apps, garbage when tested locally.
(3) Package ID stored in the MIF tail. Only valid for OTA installs or preinstalled dynamic apps, garbage when tested locally.
(4) Whether this is a static or dynamic application
*AEEModule.c:588 - (1)Installed: Unknown
(1) Installation date of the module. Only valid for OTA installs, "unknown" when tested locally.
*AEEModule.c:590 - (1)Last Used: Unknown
(1) Last used date of the module. Only valid for OTA installs, "unknown" when tested locally
*AEEModule.c:638 - (1)PT: Unknown (2)LT: Uses (3)(Unlimited)
(1) Purchase type (i.e. PT_PURCHASE, PT_SUBSCRIPTION, etc.). Identical to purchase type retrieved through ILicense.
(2) License type (i.e. LT_USES, LT_DATE, etc.). Identical to license type retrieved through ILicense.
(3) Expiration value. Meaning depends on license type.
*AEEModule.c:641 – (1)wFlags:0x0
(1) Module flags. Generally not relevant to developers.
*AEEModule.c:644 – (1)dwSize:0
(1) Size of the module package (does not include files created at runtime). Only valid for OTA installs.
*AEEModule.c:647 – (1)PHandle:0
(1) Price handle information. Only valid for OTA installs, generally not relevant to developers.
*AEEModule.c:649 – (1)HeapInUse:0/(2)Max:0
(1) The amount of heap space the module is currently using.
(2) The maximum heap space consumed by the module since BREW was last initialized.
*AEEModule.c:656 - (1)App: 0x1009ff0 (2)Type: 0 (3)Flags: 0
(1) This module defined an applet with class ID 0x1009ff0 (this line will be printed out once for every applet defined in the MIF)
(2) Extended applet type – used by carriers and OEMs, generally not relevant to developers.
(3) Applet flags (i.e. AFLAG_HIDDEN, AFLAG_TOOL, etc.).
*AEEModule.c:661 - (1)Ext: 0xABCDABCD (2)(Open)
(1) This module defined an extension with class ID 0xABCDABCD (this line will be printed out once for every extension defined in the MIF)
(2) Whether the extension is protected (closed) or unprotected (open).
In BREW 3.1.0+, BREW will also print out information about the registry. The registry is used to keep track of MIME types and registered MIME handlers; registry entries will look something like the following (numbers in parentheses added to log messages for clarity):
*AEERegistry.c:135 – (1)image/bci (2)(Viewer) (3)0x1004006
(1) MIME type handled
(2) Base class ID for the MIME handler type. If this matches one of the predefined base classes (in AEEClassIDs.h), a string description will be used.
(3) Class ID of the MIME handler.
Finally, in BREW 3.1.0+, BREW will also print information about the application stack and application history entries. This information will look something like the following (numbers in parentheses added to log messages for clarity):
*AEEShell.c:8372 – Apps
This is the start of the application stack information
*AEEShell.c:8374 - (1)1010ef6 (2)Owner: fs:/mif/mediaplayer.mif (3)State: 1
(1) There is an active application context associated with class ID 0x1010ef6
(2) The file path and name of the MIF corresponding to the module containing this class ID
(3) The current state of the application, defined as follows:
|#define APPSTATE_STOPPED||0||// Applet is stopped|
|#define APPSTATE_TOP_VISIBLE||1||// Applet is topmost visible application (foreground)|
|#define APPSTATE_SUSPENDED||2||// Applet is suspended|
|#define APPSTATE_BACKGROUND||3||// Applet is running in the background|
|#define APPSTATE_STARTING||4||// Applet is starting|
|#define APPSTATE_CLOSING||5||// Applet is closing|
*AEEShell.c:8376 – History
This is the start of the application history information
*AEEShell.c:8379 - (1)1010ef6 (2)Owner: fs:/mif/mediaplayer.mif (3)State: 1
(1) There is an active application history entry associated with class ID 0x1010ef6
(2) The file path and name of the MIF corresponding to the module containing this class ID
(3) The current state of the application, defined as above.
Dump heap (Debug number 6 on BREW 3.1.0+, debug number 9 on BREW 2.0-3.0)
Walks through all currently allocated heap nodes and displays information about each one. If the heap is corrupted, an error message will display and the heap traversal will abort. Heap nodes are printed in the following format (numbers in parentheses added to log messages for clarity):
*AEEHeap.c:1155 – (1)236 – (2)mediaplayer (3)#2208 (4)\release-builds\brewery\libdev\src\Aee\AEEBmpDecoder.c:1351 (5)(L)
(1) Size of the heap node in bytes.
(2) Owner of the heap node. For heap nodes allocated by modules, this is the name of the MIF file without the ".mif" extension. System heap allocations list the owner as "BREW".
(3) ID of the allocation. Every time memory is allocated, the current allocation ID increases by one.
(4) File and line number where the memory allocation was requested.
(5) Whether or not this heap node is locked or unlocked. Generally nodes will only be marked as unlocked after they are freed.
After printing out all the heap nodes, BREW will print a summary of heap statistics:
*AEEHeap.c:1268 - 304798 Alloc – Total
Total allocated heap memory
*AEEHeap.c:1269 - 0 OEM
Heap memory allocated to the OEM
*AEEHeap.c:1270 - 100182 BREW
Heap memory allocated to BREW
*AEEHeap.c:1271 - 204616 Apps
Heap memory allocated to applications
*AEEHeap.c:1272 - 22514 Wasted
The "wasted" quantity is overhead used in maintaining heap information – this does not refer to a memory leak.
*AEEHeap.c:1273 - 3768020 Free – Total
Total free heap memory
*AEEHeap.c:1274 - 3765792 Largest
Largest sequential allocatable heap block.
*AEEHeap.c:1275 - 3765792 Largest Non Seq.
Largest non-sequential heap block.
*AEEHeap.c:1276 - 3768000 Total Non Seq.
Total non-sequential heap memory
Dump resource cache (Debug number 7 on BREW 3.1.0+)
BREW maintains a cache for resource files (note that MIF files are resource files). Activate this debug mode to display information about the contents of BREW’s resource cache (numbers in parentheses added to log messages for clarity):
*AEERes.c:810 – (1)507 – (2)mediaplayer.bar (3)(Cached)
(1) Aging value used to determine when the file was last used
(2) Name of the file
(3) Whether this file is cached
Dump file cache (Debug number 8 on BREW 3.1.0+)
Displays information about the contents of BREW’s file cache (numbers in parentheses added to log messages for clarity):
*AEEFile.c:462 – (1)mediaplayer.bar – (2)Size: 3994 (3)Mode: 1 (4)LRU: 837 (5)(CLOSED)
(1) Name of the file
(2) Size of the file cache
(3) Mode used in opening the file (i.e. _OFM_READ, _OFM_CREATE, etc. – refer to AEEFile.h)
(4) Aging value used to determine when this file was last used
(5) Whether the file is open or closed
Close resource cache (Debug number 9 on BREW 3.1.0+, debug number * from BREW 2.1.0-3.0)
Flushes and closes all currently cached resource files. This allows for the resource files to be deleted (resource files are locked while cached).
Weight-generating output (Debug number 10 on BREW 3.1.0+, debug number # from BREW 2.1.3-3.0)
This feature is not useful for developers. When this debug mode is activate, additional log messages will be printed using DBGPRINTF(). These messages are used by handset manufacturers to generate performance related information.
BREW-directed SMS debug (Debug number 11 on BREW 3.1.0+)
Before BREW 3.1, BREW recognized app-directed SMS messages on test-enabled devices any time the "//" sequence appeared anywhere in the message payload. For non test-enabled (commercial) devices, BREW expects the "//" to be at the very beginning of the message payload. In BREW 3.1+, the test enable bit is gone and BREW defaults to the more stringent parsing performed on pre-3.1 commercial devices. This debug mode switches BREW back to the more permissive text message parsing performed on pre-3.1 test-enabled devices. Some web-based methods of sending an SMS will prepend additional information in the message payload, such as callback number or other identification information, so it will be necessary to activate this debug mode in order to properly recognize the BREW-directed SMS message during application testing.
Soft reset (Debug number 69 on BREW 3.1.0+)
Perform a soft reset of BREW (BREW restarts without power-cycling the device).
BTIL safe mode (Debug number 284 on BREW 3.1.0+)
BTIL stores port configuration information locally in the BREW EFS. In some cases this configuration information might become corrupt. If the device is no longer able to establish connectivity through BTIL, activating this debug mode will cause the BTIL configuration file to be deleted, which may restore BTIL connectivity.
Launch debug app (Debug number 324 on BREW 3.1.5+)
Many BREW APIs print helpful debug messages using DBGPRINTF(), but these messages are typically disabled in official BREW releases. Starting in BREW 3.1.5 these debug messages can be selectively turned on through the debug app. Entering this debug mode will launch the debug application allowing a developer to change the debug message settings for various BREW APIs.
Hard reset (Debug number 666 on BREW 3.1.0+)
Perform a hard reset (power-cycle) of the device.
Persist debug flags (Debug number 999 on BREW 3.1.0+)
The currently active debug modes will be saved every time BREW exits gracefully, but may be lost when there is a crash. This debug mode will trigger a save of the currently activated BREW debug modes to EFS when activated. The next time BREW starts up, the same debug modes will be enabled.
Deprecated debug modes
The following are previous debug modes that are no longer supported as of BREW 3.1.0:
Privilege failure exceptions (Debug number 4 on BREW 1.0-3.0)
This debug mode was never implemented even when it still existed.
Malloc failure exceptions (Debug number 5 on BREW 1.0-3.0)
Any time a memory allocation would have failed due to memory constraints, BREW throws an exception. This causes BREW to display an exception screen indicating the exception type, then power-cycle the device after several seconds.
Malloc test (Debug number 6 on BREW 1.0-3.0)
When this debug sequence is turned on, every 100th MALLOC will fail, even if RAM is available.
By using BREW debug sequences, a BREW developer may have an easier time diagnosing the cause of application errors. Both the method of enabling debug sequences and the available debug modes are determined by the BREW version in use, so be sure to refer to the listing above.