> You may be able to fix this by registering for > sysNotifyNormalPriority - 1, ensuring that you're notified just > after the launcher, and your SysUIAppSwitch will override the > launcher's.
Ben, that does not make sense. According to the documentation http://www.palmos.com/dev/support/docs/palmos/PalmOSReference/NotifyMgr.html#1024486 the "priority" argument of SysNotifyRegister is of type Int8. According to the include file Core/System/NotifyMgr.h, sysNotifyNormalPriority is defined as 0. Therefore, the expression "sysNotifyNormalPriority - 1" would evaluate to -1 or 0xFF, depending on how it is used later by the system. That's not "just after" - that sounds more like either "just before" or as "as late as possible" to me :-). In addition, the documentation says "In general, Palmâ recommends using a value whose least significant bits are 0 (such as 32, 64, 96, and so on)." Nevertheless, I tried using both "sysNotifyNormalPriority - 1" and "240" and the result is exactly the same - my application crashes if the notification arrives while the Launcher is running - due to the unexpected appStopEvent. :-( OK, perhaps I am blind and am not seeing something terribly obvious. Here, I made a small illustrative application. It is supposed to allow the user to turn on and off the monitoring of volume insertion (with a checkbox on its main form). Then, if the monitoring is on and a card is inserted, the application displays an information form. This application behaves pretty much like the original I'm writing - in the sense that it crashes if the notification arrives while the Launcher is running and doesn't crash otherwise. Ben, could you or anyone please look at this and see whether I am making some obvious mistake? Or is what I want to do impossible to do?! Source code, Card.c: ----------8<----Cut here----->8-------- #include <PalmOS.h> #include <VfsMgr.h> #include "CardRsc.h" #define appCreatorID 'CrMn' #define appVersionNum 0x01 #define appPrefID 0x00 #define appPrefVersionNum 0x01 #define version40 (sysMakeROMVersion (4, 0, 0, sysROMStageRelease, 0)) Boolean MainFormHandleEvent (EventPtr pEvent) { Boolean handled; FormPtr pForm; UInt32 Monitor; Err err; UInt16 cardNo; LocalID dbID; handled = false; switch (pEvent->eType) { case frmOpenEvent: pForm = FrmGetActiveForm (); FrmDrawForm (pForm); if (FtrGet (appCreatorID, 1000, &Monitor) != errNone) Monitor = false; FrmSetControlValue (pForm, FrmGetObjectIndex (pForm, kMainFormMonitorVolumeMountingCheckbox), Monitor); handled = true; break; case ctlSelectEvent: switch (pEvent->data.ctlSelect.controlID) { case kMainFormMonitorVolumeMountingCheckbox: pForm = FrmGetActiveForm (); SysCurAppDatabase (&cardNo, &dbID); if (FtrGet (appCreatorID, 1000, &Monitor) != errNone) Monitor = false; if (FrmGetControlValue (pForm, FrmGetObjectIndex (pForm, kMainFormMonitorVolumeMountingCheckbox))) { if (! Monitor) { Monitor = true; err = SysNotifyRegister (cardNo, dbID, sysNotifyVolumeMountedEvent, NULL, sysNotifyNormalPriority - 1, NULL); } } else { if (Monitor) { Monitor = false; err = SysNotifyUnregister (cardNo, dbID, sysNotifyVolumeMountedEvent, sysNotifyNormalPriority - 1); } } FrmSetControlValue (pForm, FrmGetObjectIndex (pForm, kMainFormMonitorVolumeMountingCheckbox), Monitor); FtrSet (appCreatorID, 1000, Monitor); handled = true; break; default: break; } break; default: break; } return handled; } Boolean InfoFormHandleEvent (EventPtr pEvent) { Boolean handled; FormPtr pForm; handled = false; switch (pEvent->eType) { case frmOpenEvent: pForm = FrmGetActiveForm (); FrmDrawForm (pForm); handled = true; break; default: break; } return handled; } void AppStop (void) { FrmCloseAllForms (); } Boolean AppHandleEvent (EventPtr pEvent) { UInt16 formId; FormPtr pForm; Boolean handled; handled = false; if (pEvent->eType == frmLoadEvent) { formId = pEvent->data.frmLoad.formID; pForm = FrmInitForm (formId); FrmSetActiveForm (pForm); switch (formId) { case kMainForm: FrmSetEventHandler (pForm, MainFormHandleEvent); break; case kInfoForm: FrmSetEventHandler (pForm, InfoFormHandleEvent); break; default: break; } handled = true; } return handled; } void AppEventLoop (void) { Err error; EventType event; do { EvtGetEvent (&event, evtWaitForever); if (SysHandleEvent (&event)) continue; if (MenuHandleEvent (0, &event, &error)) continue; if (AppHandleEvent (&event)) continue; FrmDispatchEvent (&event); } while (event.eType != appStopEvent); } void RegisterForNotifications (void) { UInt16 cardNo; LocalID dbID; UInt32 romVersion; UInt32 Monitor; Err err; FtrGet (sysFtrCreator, sysFtrNumROMVersion, &romVersion); if (romVersion >= version40) { if (FtrGet (appCreatorID, 1000, &Monitor) != errNone) Monitor = false; if (Monitor) { SysCurAppDatabase (&cardNo, &dbID); err = SysNotifyRegister (cardNo, dbID, sysNotifyVolumeMountedEvent, NULL, sysNotifyNormalPriority - 1, NULL); } } } void HandleNotification (SysNotifyParamType *np) { UInt32 Monitor; switch (np->notifyType) { case sysNotifyVolumeMountedEvent: if (FtrGet (appCreatorID, 1000, &Monitor) != errNone) Monitor = false; if (Monitor) { FrmGotoForm (kInfoForm); AppEventLoop (); AppStop (); } break; default: break; } } UInt32 PilotMain (UInt16 cmd, MemPtr cmdPBP, UInt16 launchFlags) { switch (cmd) { case sysAppLaunchCmdNormalLaunch: FrmGotoForm (kMainForm); AppEventLoop (); AppStop (); break; case sysAppLaunchCmdSystemReset: case sysAppLaunchCmdSyncNotify: RegisterForNotifications (); break; case sysAppLaunchCmdNotify: HandleNotification ((SysNotifyParamType *) cmdPBP); break; default: break; } return errNone; } ----------8<----Cut here----->8-------- XRD file (Card.xrd) for the PODS Resource Editor, containing the resources. Instruct the Resource Editor to generate a header file CardRsc.h in the directory where Card.c resides. ----------8<----Cut here----->8-------- <?xml version="1.0" encoding="UTF-8" standalone="yes"?> <PALMOS_RESOURCE_FILE> <FILE_PREFERENCES> <PREFS_GENERATE_HEADER> TRUE </PREFS_GENERATE_HEADER> <PREFS_HEADER_FILE> "../src/CardRsc.h" </PREFS_HEADER_FILE> <VARIABLE_TEMPLATE> "" </VARIABLE_TEMPLATE> </FILE_PREFERENCES> <FORM_RESOURCE RESOURCE_ID="1000" LOCALE="enUS" COMMENT="Main"> <FORM_ID> 1000 </FORM_ID> <BOUNDS> <LEFT> 0 </LEFT> <TOP> 0 </TOP> <WIDTH> 160 </WIDTH> <HEIGHT> 160 </HEIGHT> </BOUNDS> <USABLE> TRUE </USABLE> <MODAL> FALSE </MODAL> <SAVE_BEHIND> FALSE </SAVE_BEHIND> <HELP_ID> 0 </HELP_ID> <MENU_ID> 1000 </MENU_ID> <DEFAULT_BUTTON> 0 </DEFAULT_BUTTON> <TITLE_ICON> FALSE </TITLE_ICON> <TITLE_BAR_FOCUSABLE> FALSE </TITLE_BAR_FOCUSABLE> <FORM_OBJECTS> <FORM_TITLE> <TEXT> "Card" </TEXT> </FORM_TITLE> <FORM_CHECKBOX COMMENT="Monitor"> <ID> 1000 </ID> <BOUNDS> <LEFT> 15 </LEFT> <TOP> 31 </TOP> <WIDTH> 126 </WIDTH> <HEIGHT> 12 </HEIGHT> </BOUNDS> <USABLE> TRUE </USABLE> <ENABLED> TRUE </ENABLED> <TEXT> "Monitor Volume Mounting" </TEXT> <FONT_ID> STD_FONT </FONT_ID> <GROUP_ID> 0 </GROUP_ID> <SELECTED> FALSE </SELECTED> </FORM_CHECKBOX> </FORM_OBJECTS> </FORM_RESOURCE> <FORM_RESOURCE RESOURCE_ID="1100" COMMENT="Info"> <FORM_ID> 1100 </FORM_ID> <BOUNDS> <LEFT> 0 </LEFT> <TOP> 0 </TOP> <WIDTH> 160 </WIDTH> <HEIGHT> 160 </HEIGHT> </BOUNDS> <USABLE> TRUE </USABLE> <MODAL> FALSE </MODAL> <SAVE_BEHIND> FALSE </SAVE_BEHIND> <HELP_ID> 0 </HELP_ID> <MENU_ID> 0 </MENU_ID> <DEFAULT_BUTTON> 0 </DEFAULT_BUTTON> <TITLE_ICON> FALSE </TITLE_ICON> <TITLE_BAR_FOCUSABLE> FALSE </TITLE_BAR_FOCUSABLE> <FORM_OBJECTS> <FORM_TITLE> <TEXT> "Volume Info" </TEXT> </FORM_TITLE> <FORM_LABEL COMMENT="Mounted"> <ID> 1000 </ID> <LOCATION> <X> 24 </X> <Y> 25 </Y> </LOCATION> <USABLE> TRUE </USABLE> <FONT_ID> STD_FONT </FONT_ID> <TEXT> "A volume was just mounted." </TEXT> </FORM_LABEL> <FORM_LABEL COMMENT="Volume Label"> <ID> 1001 </ID> <LOCATION> <X> 52 </X> <Y> 40 </Y> </LOCATION> <USABLE> FALSE </USABLE> <FONT_ID> STD_FONT </FONT_ID> <TEXT> "Volume Label:" </TEXT> </FORM_LABEL> <FORM_FIELD COMMENT="Volume Label"> <ID> 1002 </ID> <BOUNDS> <LEFT> 5 </LEFT> <TOP> 58 </TOP> <WIDTH> 150 </WIDTH> <HEIGHT> 12 </HEIGHT> </BOUNDS> <USABLE> FALSE </USABLE> <EDITABLE> FALSE </EDITABLE> <SINGLE_LINE> TRUE </SINGLE_LINE> <DYNAMIC_SIZE> FALSE </DYNAMIC_SIZE> <UNDERLINE> NO_UNDERLINE </UNDERLINE> <JUSTIFICATION> LEFT_ALIGN </JUSTIFICATION> <AUTO_SHIFT> FALSE </AUTO_SHIFT> <HAS_SCROLLBAR> FALSE </HAS_SCROLLBAR> <NUMERIC> FALSE </NUMERIC> <MAX_CHARS> 32 </MAX_CHARS> <FONT_ID> STD_FONT </FONT_ID> <MAX_VISIBLE_LINES> 1 </MAX_VISIBLE_LINES> </FORM_FIELD> </FORM_OBJECTS> </FORM_RESOURCE> </PALMOS_RESOURCE_FILE> ----------8<----Cut here----->8-------- If the above two source are too manged to be useful, e-mail me and I'll send you the original files as attachments. WARNING: If somebody wants to try the above on a real device, please have in mind that it sets a feature (ID = 'CrMn', index = 1000) and never unregisters it. I personally dislike programs that don't clean up after themselves but this is just an illustrative application and I didn't want to clutter the code that illustrates the problem with additional handling of buttons and forms to remove the feature. Regards, Vesselin -- For information on using the Palm Developer Forums, or to unsubscribe, please see http://www.palmos.com/dev/support/forums/
