1 // Registrar.cpp 2 3 #include "Debug.h" 4 5 #include <Application.h> 6 #include <Message.h> 7 #include <OS.h> 8 #include <RegistrarDefs.h> 9 10 #include "ClipboardHandler.h" 11 #include "EventQueue.h" 12 #include "MessageEvent.h" 13 #include "MessageRunnerManager.h" 14 #include "MIMEManager.h" 15 #include "Registrar.h" 16 #include "TRoster.h" 17 18 /*! 19 \class Registrar 20 \brief The application class of the registrar. 21 22 Glues the registrar services together and dispatches the roster messages. 23 */ 24 25 //! Name of the event queue. 26 static const char *kEventQueueName = "timer_thread"; 27 28 //! Time interval between two roster sanity checks (1 s). 29 static const bigtime_t kRosterSanityEventInterval = 1000000LL; 30 31 // constructor 32 /*! \brief Creates the registrar application class. 33 */ 34 Registrar::Registrar() 35 : BApplication(kRegistrarSignature), 36 fRoster(NULL), 37 fClipboardHandler(NULL), 38 fMIMEManager(NULL), 39 fEventQueue(NULL), 40 fMessageRunnerManager(NULL), 41 fSanityEvent(NULL) 42 { 43 FUNCTION_START(); 44 } 45 46 // destructor 47 /*! \brief Frees all resources associated with the registrar. 48 49 All registrar services, that haven't been shut down earlier, are 50 terminated. 51 */ 52 Registrar::~Registrar() 53 { 54 FUNCTION_START(); 55 Lock(); 56 fEventQueue->Die(); 57 delete fMessageRunnerManager; 58 delete fEventQueue; 59 delete fSanityEvent; 60 fMIMEManager->Lock(); 61 fMIMEManager->Quit(); 62 RemoveHandler(fClipboardHandler); 63 delete fClipboardHandler; 64 delete fRoster; 65 // Invalidate the global be_roster, so that the BApplication destructor 66 // won't dead-lock when sending a message to itself. 67 BPrivate::init_registrar_roster(BMessenger(), BMessenger()); 68 FUNCTION_END(); 69 } 70 71 // MessageReceived 72 /*! \brief Overrides the super class version to dispatch roster specific 73 messages. 74 \param message The message to be handled 75 */ 76 void 77 Registrar::MessageReceived(BMessage *message) 78 { 79 // FUNCTION_START(); 80 switch (message->what) { 81 // general requests 82 case B_REG_GET_MIME_MESSENGER: 83 { 84 PRINT(("B_REG_GET_MIME_MESSENGER\n")); 85 BMessenger messenger(NULL, fMIMEManager); 86 BMessage reply(B_REG_SUCCESS); 87 reply.AddMessenger("messenger", messenger); 88 message->SendReply(&reply); 89 break; 90 } 91 case B_REG_GET_CLIPBOARD_MESSENGER: 92 { 93 PRINT(("B_REG_GET_CLIPBOARD_MESSENGER\n")); 94 BMessenger messenger(fClipboardHandler); 95 BMessage reply(B_REG_SUCCESS); 96 reply.AddMessenger("messenger", messenger); 97 message->SendReply(&reply); 98 break; 99 } 100 // roster requests 101 case B_REG_ADD_APP: 102 fRoster->HandleAddApplication(message); 103 break; 104 case B_REG_COMPLETE_REGISTRATION: 105 fRoster->HandleCompleteRegistration(message); 106 break; 107 case B_REG_IS_APP_PRE_REGISTERED: 108 fRoster->HandleIsAppPreRegistered(message); 109 break; 110 case B_REG_REMOVE_PRE_REGISTERED_APP: 111 fRoster->HandleRemovePreRegApp(message); 112 break; 113 case B_REG_REMOVE_APP: 114 fRoster->HandleRemoveApp(message); 115 break; 116 case B_REG_SET_THREAD_AND_TEAM: 117 fRoster->HandleSetThreadAndTeam(message); 118 break; 119 case B_REG_SET_SIGNATURE: 120 fRoster->HandleSetSignature(message); 121 break; 122 case B_REG_GET_APP_INFO: 123 fRoster->HandleGetAppInfo(message); 124 break; 125 case B_REG_GET_APP_LIST: 126 fRoster->HandleGetAppList(message); 127 break; 128 case B_REG_ACTIVATE_APP: 129 fRoster->HandleActivateApp(message); 130 break; 131 case B_REG_BROADCAST: 132 fRoster->HandleBroadcast(message); 133 break; 134 case B_REG_START_WATCHING: 135 fRoster->HandleStartWatching(message); 136 break; 137 case B_REG_STOP_WATCHING: 138 fRoster->HandleStopWatching(message); 139 break; 140 case B_REG_GET_RECENT_DOCUMENTS: 141 fRoster->HandleGetRecentDocuments(message); 142 break; 143 case B_REG_GET_RECENT_FOLDERS: 144 fRoster->HandleGetRecentFolders(message); 145 break; 146 case B_REG_GET_RECENT_APPS: 147 fRoster->HandleGetRecentApps(message); 148 break; 149 case B_REG_ADD_TO_RECENT_DOCUMENTS: 150 fRoster->HandleAddToRecentDocuments(message); 151 break; 152 case B_REG_ADD_TO_RECENT_FOLDERS: 153 fRoster->HandleAddToRecentFolders(message); 154 break; 155 case B_REG_ADD_TO_RECENT_APPS: 156 fRoster->HandleAddToRecentApps(message); 157 break; 158 case B_REG_CLEAR_RECENT_DOCUMENTS: 159 fRoster->ClearRecentDocuments(); 160 break; 161 case B_REG_CLEAR_RECENT_FOLDERS: 162 fRoster->ClearRecentFolders(); 163 break; 164 case B_REG_CLEAR_RECENT_APPS: 165 fRoster->ClearRecentApps(); 166 break; 167 case B_REG_LOAD_RECENT_LISTS: 168 fRoster->HandleLoadRecentLists(message); 169 break; 170 case B_REG_SAVE_RECENT_LISTS: 171 fRoster->HandleSaveRecentLists(message); 172 break; 173 // message runner requests 174 case B_REG_REGISTER_MESSAGE_RUNNER: 175 fMessageRunnerManager->HandleRegisterRunner(message); 176 break; 177 case B_REG_UNREGISTER_MESSAGE_RUNNER: 178 fMessageRunnerManager->HandleUnregisterRunner(message); 179 break; 180 case B_REG_SET_MESSAGE_RUNNER_PARAMS: 181 fMessageRunnerManager->HandleSetRunnerParams(message); 182 break; 183 case B_REG_GET_MESSAGE_RUNNER_INFO: 184 fMessageRunnerManager->HandleGetRunnerInfo(message); 185 break; 186 // internal messages 187 case B_REG_ROSTER_SANITY_EVENT: 188 fRoster->CheckSanity(); 189 fSanityEvent->SetTime(system_time() + kRosterSanityEventInterval); 190 fEventQueue->AddEvent(fSanityEvent); 191 break; 192 default: 193 BApplication::MessageReceived(message); 194 break; 195 } 196 // FUNCTION_END(); 197 } 198 199 // ReadyToRun 200 /*! \brief Overrides the super class version to initialize the registrar 201 services. 202 */ 203 void 204 Registrar::ReadyToRun() 205 { 206 FUNCTION_START(); 207 // create roster 208 fRoster = new TRoster; 209 fRoster->Init(); 210 // create clipboard handler 211 fClipboardHandler = new ClipboardHandler; 212 AddHandler(fClipboardHandler); 213 // create MIME manager 214 fMIMEManager = new MIMEManager; 215 fMIMEManager->Run(); 216 // create message runner manager 217 fEventQueue = new EventQueue(kEventQueueName); 218 fMessageRunnerManager = new MessageRunnerManager(fEventQueue); 219 // init the global be_roster 220 BPrivate::init_registrar_roster(be_app_messenger, 221 BMessenger(NULL, fMIMEManager)); 222 // create and schedule the sanity message event 223 fSanityEvent = new MessageEvent(system_time() + kRosterSanityEventInterval, 224 this, B_REG_ROSTER_SANITY_EVENT); 225 fSanityEvent->SetAutoDelete(false); 226 fEventQueue->AddEvent(fSanityEvent); 227 FUNCTION_END(); 228 } 229 230 // QuitRequested 231 /*! \brief Overrides the super class version to avoid termination of the 232 registrar until the system shutdown. 233 */ 234 bool 235 Registrar::QuitRequested() 236 { 237 FUNCTION_START(); 238 // The final registrar must not quit. At least not that easily. ;-) 239 return BApplication::QuitRequested(); 240 } 241 242 // GetEventQueue 243 /*! \brief Returns the registrar's event queue. 244 \return The registrar's event queue. 245 */ 246 EventQueue* 247 Registrar::GetEventQueue() const 248 { 249 return fEventQueue; 250 } 251 252 // App 253 /*! \brief Returns the Registrar application object. 254 \return The Registrar application object. 255 */ 256 Registrar* 257 Registrar::App() 258 { 259 return dynamic_cast<Registrar*>(be_app); 260 } 261 262 263 // init_registrar_roster 264 /*! \brief Initializes the global \a be_roster. 265 266 While this is done automagically for all other applications while libbe 267 initialization, the registrar needs to help out a bit. 268 269 \param mainMessenger A BMessenger targeting the registrar application. 270 \param mimeMessenger A BMessenger targeting the MIME manager. 271 */ 272 void 273 BPrivate::init_registrar_roster(BMessenger mainMessenger, 274 BMessenger mimeMessenger) 275 { 276 BRoster *roster = const_cast<BRoster*>(be_roster); 277 roster->fMess = mainMessenger; 278 roster->fMimeMess = mimeMessenger; 279 } 280 281 282 // main 283 /*! \brief Creates and runs the registrar application. 284 285 The main thread is renamed. 286 287 \return 0. 288 */ 289 int 290 main() 291 { 292 FUNCTION_START(); 293 // rename the main thread 294 rename_thread(find_thread(NULL), kRosterThreadName); 295 // create and run the registrar application 296 Registrar *app = new Registrar(); 297 PRINT(("app->Run()...\n")); 298 app->Run(); 299 PRINT(("delete app...\n")); 300 delete app; 301 FUNCTION_END(); 302 return 0; 303 } 304 305