diff --git a/src/kits/app/LinkReceiver.cpp b/src/kits/app/LinkReceiver.cpp index ad20ee9b39..3a7b0e1793 100644 --- a/src/kits/app/LinkReceiver.cpp +++ b/src/kits/app/LinkReceiver.cpp @@ -1,5 +1,5 @@ /* - * Copyright 2001-2006, Haiku. + * Copyright 2001-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -161,11 +161,14 @@ LinkReceiver::AdjustReplyBuffer(bigtime_t timeout) fRecvBufferSize = kInitialBufferSize; } else { STRACE(("info: LinkReceiver getting port_buffer_size().\n")); + ssize_t bufferSize; - if (timeout == B_INFINITE_TIMEOUT) - bufferSize = port_buffer_size(fReceivePort); - else - bufferSize = port_buffer_size_etc(fReceivePort, B_TIMEOUT, timeout); + do { + bufferSize = port_buffer_size_etc(fReceivePort, + timeout == B_INFINITE_TIMEOUT ? B_RELATIVE_TIMEOUT : 0, + timeout); + } while (bufferSize == B_INTERRUPTED); + STRACE(("info: LinkReceiver got port_buffer_size() = %ld.\n", bufferSize)); if (bufferSize < 0) diff --git a/src/servers/app/AppServer.cpp b/src/servers/app/AppServer.cpp index 597755be88..262862d614 100644 --- a/src/servers/app/AppServer.cpp +++ b/src/servers/app/AppServer.cpp @@ -1,5 +1,5 @@ /* - * Copyright (c) 2001-2006, Haiku, Inc. + * Copyright (c) 2001-2007, Haiku, Inc. * Distributed under the terms of the MIT license. * * Authors: @@ -113,67 +113,6 @@ AppServer::RunLooper() } -#if 0 -/*! - \brief Starts Input Server -*/ -void -AppServer::_LaunchInputServer() -{ - // We are supposed to start the input_server, but it's a BApplication - // that depends on the registrar running, which is started after app_server - // so we wait on roster thread to launch the input server - - fISThreadID = B_ERROR; - - while (!BRoster::Private().IsMessengerValid(false) && !fQuitting) { - snooze(250000); - BRoster::Private::DeleteBeRoster(); - BRoster::Private::InitBeRoster(); - } - - if (fQuitting) - return; - - // we use an area for cursor data communication with input_server - // area id and sem id are sent to the input_server - - if (fCursorArea < B_OK) - fCursorArea = create_area("isCursor", (void**) &fCursorAddr, B_ANY_ADDRESS, B_PAGE_SIZE, B_FULL_LOCK, B_READ_AREA | B_WRITE_AREA); - if (fCursorSem < B_OK) - fCursorSem = create_sem(0, "isSem"); - - int32 arg_c = 1; - char **arg_v = (char **)malloc(sizeof(char *) * (arg_c + 1)); -#if TEST_MODE - arg_v[0] = strdup("/boot/home/svnhaiku/trunk/distro/x86.R1/beos/system/servers/input_server"); -#else - arg_v[0] = strdup("/system/servers/input_server"); -#endif - arg_v[1] = NULL; - fISThreadID = load_image(arg_c, (const char**)arg_v, (const char **)environ); - free(arg_v[0]); - - int32 tmpbuf[2] = {fCursorSem, fCursorArea}; - int32 code = 0; - send_data(fISThreadID, code, (void *)tmpbuf, sizeof(tmpbuf)); - - resume_thread(fISThreadID); - setpgid(fISThreadID, 0); - - // we receive - - thread_id sender; - code = receive_data(&sender, (void *)tmpbuf, sizeof(tmpbuf)); - fISASPort = tmpbuf[0]; - fISPort = tmpbuf[1]; - - // if at any time, one of these ports is error prone, it might mean input_server is gone - // then relaunch input_server -} -#endif - - /*! \brief Creates a desktop object for an authorized user */ @@ -299,12 +238,6 @@ AppServer::_DispatchMessage(int32 code, BPrivate::LinkReceiver& msg) // #pragma mark - -/*! - \brief Entry function to run the entire server - \param argc Number of command-line arguments present - \param argv String array of the command-line arguments - \return -1 if the app_server is already running, 0 if everything's OK. -*/ int main(int argc, char** argv) { diff --git a/src/servers/app/MessageLooper.cpp b/src/servers/app/MessageLooper.cpp index 62360534e4..6bcc540756 100644 --- a/src/servers/app/MessageLooper.cpp +++ b/src/servers/app/MessageLooper.cpp @@ -118,7 +118,12 @@ MessageLooper::_PrepareQuit() void MessageLooper::_GetLooperName(char* name, size_t length) { - strcpy(name, "unnamed looper"); + sem_id semaphore = Sem(); + sem_info info; + if (get_sem_info(semaphore, &info) == B_OK) + strlcpy(name, info.name, length); + else + strlcpy(name, "unnamed looper", length); } @@ -138,7 +143,10 @@ MessageLooper::_MessageLooper() status_t status = receiver.GetNextMessage(code); if (status < B_OK) { // that shouldn't happen, it's our port - printf("Someone deleted our message port!\n"); + char name[256]; + _GetLooperName(name, 256); + printf("MessageLooper \"%s\": Someone deleted our message port %ld, %s!\n", + name, receiver.Port(), strerror(status)); break; } diff --git a/src/servers/registrar/RosterAppInfo.cpp b/src/servers/registrar/RosterAppInfo.cpp index 354b060326..7e012a03ec 100644 --- a/src/servers/registrar/RosterAppInfo.cpp +++ b/src/servers/registrar/RosterAppInfo.cpp @@ -1,63 +1,46 @@ -//------------------------------------------------------------------------------ -// Copyright (c) 2001-2002, OpenBeOS -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the "Software"), -// to deal in the Software without restriction, including without limitation -// the rights to use, copy, modify, merge, publish, distribute, sublicense, -// and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in -// all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER -// DEALINGS IN THE SOFTWARE. -// -// File Name: RosterAppInfo.cpp -// Author: Ingo Weinhold (bonefish@users.sf.net) -// Description: An extended app_info. -//------------------------------------------------------------------------------ +/* + * Copyright 2001-2007, Ingo Weinhold, bonefish@users.sf.net. + * Distributed under the terms of the MIT License. + */ -#include - -#include +//! An extended app_info. #include "RosterAppInfo.h" +#include +#include + + using std::nothrow; + // constructor RosterAppInfo::RosterAppInfo() - : app_info(), - state(APP_STATE_UNREGISTERED), - token(0), - registration_time(0) + : app_info(), + state(APP_STATE_UNREGISTERED), + token(0), + registration_time(0) { } + // Init void RosterAppInfo::Init(thread_id thread, team_id team, port_id port, uint32 flags, - const entry_ref *ref, const char *signature) + const entry_ref *ref, const char *signature) { this->thread = thread; this->team = team; this->port = port; this->flags = flags; this->ref = *ref; - if (signature) { - strncpy(this->signature, signature, B_MIME_TYPE_LENGTH - 1); - this->signature[B_MIME_TYPE_LENGTH - 1] = '\0'; - } else + if (signature) + strlcpy(this->signature, signature, B_MIME_TYPE_LENGTH); + else this->signature[0] = '\0'; } + // Clone RosterAppInfo * RosterAppInfo::Clone() const @@ -70,3 +53,13 @@ RosterAppInfo::Clone() const clone->registration_time = registration_time; return clone; } + + +// IsRunning +bool +RosterAppInfo::IsRunning() const +{ + team_info teamInfo; + return get_team_info(team, &teamInfo) == B_OK; +} + diff --git a/src/servers/registrar/RosterAppInfo.h b/src/servers/registrar/RosterAppInfo.h index c8a536554d..40dd8e238a 100644 --- a/src/servers/registrar/RosterAppInfo.h +++ b/src/servers/registrar/RosterAppInfo.h @@ -1,29 +1,7 @@ -//------------------------------------------------------------------------------ -// Copyright (c) 2001-2002, OpenBeOS -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the "Software"), -// to deal in the Software without restriction, including without limitation -// the rights to use, copy, modify, merge, publish, distribute, sublicense, -// and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in -// all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER -// DEALINGS IN THE SOFTWARE. -// -// File Name: RosterAppInfo.h -// Author: Ingo Weinhold (bonefish@users.sf.net) -// Description: An extended app_info. -//------------------------------------------------------------------------------ - +/* + * Copyright 2001-2007, Ingo Weinhold, bonefish@users.sf.net. + * Distributed under the terms of the MIT License. + */ #ifndef ROSTER_APP_INFO_H #define ROSTER_APP_INFO_H @@ -45,9 +23,10 @@ struct RosterAppInfo : app_info { RosterAppInfo(); void Init(thread_id thread, team_id team, port_id port, uint32 flags, - const entry_ref *ref, const char *signature); + const entry_ref *ref, const char *signature); RosterAppInfo *Clone() const; + bool IsRunning() const; }; #endif // ROSTER_APP_INFO_H diff --git a/src/servers/registrar/TRoster.cpp b/src/servers/registrar/TRoster.cpp index 6f442d68d5..1857eb170f 100644 --- a/src/servers/registrar/TRoster.cpp +++ b/src/servers/registrar/TRoster.cpp @@ -179,24 +179,26 @@ PRINT(("full registration: %d\n", fullReg)); uint32 token = 0; uint32 launchFlags = flags & B_LAUNCH_MASK; + BEntry entry(&ref); + if (!entry.Exists()) + SET_ERROR(error, B_ENTRY_NOT_FOUND); + + if (error == B_OK) + _ValidateRunning(ref, signature); // entry_ref if (error == B_OK) { - // the entry_ref must be valid - if (BEntry(&ref).Exists()) { PRINT(("flags: %lx\n", flags)); PRINT(("ref: %ld, %lld, %s\n", ref.device, ref.directory, ref.name)); - // check single/exclusive launchers - RosterAppInfo *info = NULL; - if ((launchFlags == B_SINGLE_LAUNCH - || launchFlags == B_EXCLUSIVE_LAUNCH) - && (((info = fRegisteredApps.InfoFor(&ref))) - || ((info = fEarlyPreRegisteredApps.InfoFor(&ref))))) { - SET_ERROR(error, B_ALREADY_RUNNING); - otherTeam = info->team; - } - } else - SET_ERROR(error, B_ENTRY_NOT_FOUND); + // check single/exclusive launchers + RosterAppInfo *info = NULL; + if ((launchFlags == B_SINGLE_LAUNCH + || launchFlags == B_EXCLUSIVE_LAUNCH) + && ((info = info = fRegisteredApps.InfoFor(&ref)) != NULL + || (info = fEarlyPreRegisteredApps.InfoFor(&ref)) != NULL)) { + SET_ERROR(error, B_ALREADY_RUNNING); + otherTeam = info->team; + } } // signature @@ -1274,8 +1276,7 @@ TRoster::CheckSanity() // not early (pre-)registered applications AppInfoList obsoleteApps; for (AppInfoList::Iterator it = fRegisteredApps.It(); it.IsValid(); ++it) { - team_info teamInfo; - if (get_team_info((*it)->team, &teamInfo) != B_OK) + if (!(*it)->IsRunning()) obsoleteApps.AddInfo(*it); } // remove the apps @@ -1750,7 +1751,30 @@ TRoster::_HandleGetRecentEntries(BMessage *request) FUNCTION_END(); } -// _IsSystemApp + +/*! + \brief Checks all registered apps for \a ref and \a signature if + they are still alive, and removes those that aren't. +*/ +void +TRoster::_ValidateRunning(const entry_ref& ref, const char* signature) +{ + while (true) { + // get info via ref or signature + RosterAppInfo* info = fRegisteredApps.InfoFor(&ref); + if (info == NULL && signature != NULL) + info = fRegisteredApps.InfoFor(signature); + + // if app is alive or does not exist, we can exit + if (info == NULL || info->IsRunning()) + return; + + RemoveApp(info); + delete info; + } +} + + bool TRoster::_IsSystemApp(RosterAppInfo *info) const { diff --git a/src/servers/registrar/TRoster.h b/src/servers/registrar/TRoster.h index ec01843cf4..e73f02c3b6 100644 --- a/src/servers/registrar/TRoster.h +++ b/src/servers/registrar/TRoster.h @@ -84,20 +84,20 @@ private: void _AppDeactivated(RosterAppInfo *info); // helper functions - static status_t _AddMessageAppInfo(BMessage *message, - const app_info *info); - static status_t _AddMessageWatchingInfo(BMessage *message, - const app_info *info); + static status_t _AddMessageAppInfo(BMessage* message, const app_info* info); + static status_t _AddMessageWatchingInfo(BMessage* message, + const app_info* info); uint32 _NextToken(); void _AddIARRequest(IARRequestMap& map, int32 key, BMessage* request); - void _ReplyToIARRequests(BMessageQueue *requests, - const RosterAppInfo *info); - void _ReplyToIARRequest(BMessage *request, const RosterAppInfo *info); + void _ReplyToIARRequests(BMessageQueue* requests, + const RosterAppInfo* info); + void _ReplyToIARRequest(BMessage* request, const RosterAppInfo* info); - void _HandleGetRecentEntries(BMessage *request); + void _HandleGetRecentEntries(BMessage* request); - bool _IsSystemApp(RosterAppInfo *info) const; + void _ValidateRunning(const entry_ref& ref, const char* signature); + bool _IsSystemApp(RosterAppInfo* info) const; status_t _LoadRosterSettings(const char *path = NULL); status_t _SaveRosterSettings(const char *path = NULL); @@ -109,7 +109,7 @@ private: AppInfoList fEarlyPreRegisteredApps; IARRequestMap fIARRequestsByID; IARRequestMap fIARRequestsByToken; - RosterAppInfo *fActiveApp; + RosterAppInfo* fActiveApp; WatchingService fWatchingService; RecentApps fRecentApps; RecentEntries fRecentDocuments;