The app_server is now a regular BServer.
This commit is contained in:
@@ -30,8 +30,6 @@ thread_id main_thread_for(team_id team);
|
|||||||
|
|
||||||
bool is_app_showing_modal_window(team_id team);
|
bool is_app_showing_modal_window(team_id team);
|
||||||
|
|
||||||
void invalidate_server_port();
|
|
||||||
port_id get_app_server_port();
|
|
||||||
status_t create_desktop_connection(ServerLink* link, const char* name,
|
status_t create_desktop_connection(ServerLink* link, const char* name,
|
||||||
int32 capacity);
|
int32 capacity);
|
||||||
|
|
||||||
|
|||||||
+17
-41
@@ -1,8 +1,9 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2001-2011, Haiku, Inc.
|
* Copyright 2001-2015, Haiku, Inc.
|
||||||
* Distributed under the terms of the MIT License.
|
* Distributed under the terms of the MIT License.
|
||||||
*
|
*
|
||||||
* Authors:
|
* Authors:
|
||||||
|
* Axel Dörfler, [email protected]
|
||||||
* Ingo Weinhold, bonefish@@users.sf.net
|
* Ingo Weinhold, bonefish@@users.sf.net
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@@ -16,6 +17,7 @@
|
|||||||
|
|
||||||
#include <Entry.h>
|
#include <Entry.h>
|
||||||
#include <image.h>
|
#include <image.h>
|
||||||
|
#include <Messenger.h>
|
||||||
#include <OS.h>
|
#include <OS.h>
|
||||||
|
|
||||||
#include <ServerLink.h>
|
#include <ServerLink.h>
|
||||||
@@ -174,60 +176,34 @@ is_app_showing_modal_window(team_id team)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static port_id sServerPort = -1;
|
|
||||||
|
|
||||||
|
|
||||||
void
|
|
||||||
invalidate_server_port()
|
|
||||||
{
|
|
||||||
sServerPort = -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
port_id
|
|
||||||
get_app_server_port()
|
|
||||||
{
|
|
||||||
if (sServerPort < 0) {
|
|
||||||
// No need for synchronization - in the worst case, we'll call
|
|
||||||
// find_port() twice.
|
|
||||||
sServerPort = find_port(SERVER_PORT_NAME);
|
|
||||||
}
|
|
||||||
|
|
||||||
return sServerPort;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*! Creates a connection with the desktop.
|
/*! Creates a connection with the desktop.
|
||||||
*/
|
*/
|
||||||
status_t
|
status_t
|
||||||
create_desktop_connection(ServerLink* link, const char* name, int32 capacity)
|
create_desktop_connection(ServerLink* link, const char* name, int32 capacity)
|
||||||
{
|
{
|
||||||
port_id serverPort = get_app_server_port();
|
|
||||||
if (serverPort < 0)
|
|
||||||
return serverPort;
|
|
||||||
|
|
||||||
// Create the port so that the app_server knows where to send messages
|
// Create the port so that the app_server knows where to send messages
|
||||||
port_id clientPort = create_port(capacity, name);
|
port_id clientPort = create_port(capacity, name);
|
||||||
if (clientPort < 0)
|
if (clientPort < 0)
|
||||||
return clientPort;
|
return clientPort;
|
||||||
|
|
||||||
link->SetTo(serverPort, clientPort);
|
link->SetReceiverPort(clientPort);
|
||||||
|
|
||||||
link->StartMessage(AS_GET_DESKTOP);
|
BMessage request(AS_GET_DESKTOP);
|
||||||
link->Attach<port_id>(clientPort);
|
request.AddInt32("user", getuid());
|
||||||
link->Attach<int32>(getuid());
|
request.AddInt32("version", AS_PROTOCOL_VERSION);
|
||||||
link->AttachString(getenv("TARGET_SCREEN"));
|
request.AddString("target", getenv("TARGET_SCREEN"));
|
||||||
link->Attach<int32>(AS_PROTOCOL_VERSION);
|
|
||||||
|
|
||||||
int32 code;
|
BMessenger server("application/x-vnd.Haiku-app_server");
|
||||||
if (link->FlushWithReply(code) != B_OK || code != B_OK) {
|
BMessage reply;
|
||||||
link->SetSenderPort(-1);
|
status_t status = server.SendMessage(&request, &reply);
|
||||||
return B_ERROR;
|
if (status != B_OK)
|
||||||
}
|
return status;
|
||||||
|
|
||||||
link->Read<port_id>(&serverPort);
|
port_id desktopPort = reply.GetInt32("port", B_ERROR);
|
||||||
link->SetSenderPort(serverPort);
|
if (desktopPort < 0)
|
||||||
|
return desktopPort;
|
||||||
|
|
||||||
|
link->SetSenderPort(desktopPort);
|
||||||
return B_OK;
|
return B_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1410,7 +1410,6 @@ BApplication::_ReconnectToServer()
|
|||||||
{
|
{
|
||||||
delete_port(fServerLink->SenderPort());
|
delete_port(fServerLink->SenderPort());
|
||||||
delete_port(fServerLink->ReceiverPort());
|
delete_port(fServerLink->ReceiverPort());
|
||||||
invalidate_server_port();
|
|
||||||
|
|
||||||
if (_ConnectToServer() != B_OK)
|
if (_ConnectToServer() != B_OK)
|
||||||
debugger("Can't reconnect to app server!");
|
debugger("Can't reconnect to app server!");
|
||||||
|
|||||||
+71
-116
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2001-2011, Haiku, Inc.
|
* Copyright 2001-2015, Haiku, Inc.
|
||||||
* Distributed under the terms of the MIT license.
|
* Distributed under the terms of the MIT license.
|
||||||
*
|
*
|
||||||
* Authors:
|
* Authors:
|
||||||
@@ -35,7 +35,6 @@
|
|||||||
|
|
||||||
// Globals
|
// Globals
|
||||||
port_id gAppServerPort;
|
port_id gAppServerPort;
|
||||||
static AppServer* sAppServer;
|
|
||||||
BTokenSpace gTokenSpace;
|
BTokenSpace gTokenSpace;
|
||||||
uint32 gAppServerSIMDFlags = 0;
|
uint32 gAppServerSIMDFlags = 0;
|
||||||
|
|
||||||
@@ -46,23 +45,13 @@ uint32 gAppServerSIMDFlags = 0;
|
|||||||
spawns the main housekeeping threads, loads user preferences for the UI
|
spawns the main housekeeping threads, loads user preferences for the UI
|
||||||
and decorator, and allocates various locks.
|
and decorator, and allocates various locks.
|
||||||
*/
|
*/
|
||||||
AppServer::AppServer()
|
AppServer::AppServer(status_t* status)
|
||||||
:
|
:
|
||||||
MessageLooper("app_server"),
|
BServer("application/x-vnd.Haiku-app_server", "picasso", -1, false, status),
|
||||||
fMessagePort(-1),
|
|
||||||
fDesktops(),
|
|
||||||
fDesktopLock("AppServerDesktopLock")
|
fDesktopLock("AppServerDesktopLock")
|
||||||
{
|
{
|
||||||
openlog("app_server", 0, LOG_DAEMON);
|
openlog("app_server", 0, LOG_DAEMON);
|
||||||
|
|
||||||
fMessagePort = create_port(DEFAULT_MONITOR_PORT_SIZE, SERVER_PORT_NAME);
|
|
||||||
if (fMessagePort < B_OK)
|
|
||||||
debugger("app_server could not create message port");
|
|
||||||
|
|
||||||
fLink.SetReceiverPort(fMessagePort);
|
|
||||||
|
|
||||||
sAppServer = this;
|
|
||||||
|
|
||||||
gInputManager = new InputManager();
|
gInputManager = new InputManager();
|
||||||
|
|
||||||
// Create the font server and scan the proper directories.
|
// Create the font server and scan the proper directories.
|
||||||
@@ -98,10 +87,70 @@ AppServer::~AppServer()
|
|||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
AppServer::RunLooper()
|
AppServer::MessageReceived(BMessage* message)
|
||||||
{
|
{
|
||||||
rename_thread(find_thread(NULL), "picasso");
|
switch (message->what) {
|
||||||
_message_thread((void*)this);
|
case AS_GET_DESKTOP:
|
||||||
|
{
|
||||||
|
Desktop* desktop = NULL;
|
||||||
|
|
||||||
|
int32 userID = message->GetInt32("user", 0);
|
||||||
|
int32 version = message->GetInt32("version", 0);
|
||||||
|
const char* targetScreen = message->GetString("target");
|
||||||
|
|
||||||
|
if (version != AS_PROTOCOL_VERSION) {
|
||||||
|
syslog(LOG_ERR, "Application for user %" B_PRId32 " does not "
|
||||||
|
"support the current server protocol.\n", userID);
|
||||||
|
} else {
|
||||||
|
desktop = _FindDesktop(userID, targetScreen);
|
||||||
|
if (desktop == NULL) {
|
||||||
|
// we need to create a new desktop object for this user
|
||||||
|
// TODO: test if the user exists on the system
|
||||||
|
// TODO: maybe have a separate AS_START_DESKTOP_SESSION for
|
||||||
|
// authorizing the user
|
||||||
|
desktop = _CreateDesktop(userID, targetScreen);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
BMessage reply;
|
||||||
|
if (desktop != NULL)
|
||||||
|
reply.AddInt32("port", desktop->MessagePort());
|
||||||
|
else
|
||||||
|
reply.what = (uint32)B_ERROR;
|
||||||
|
|
||||||
|
message->SendReply(&reply);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
default:
|
||||||
|
// We don't allow application scripting
|
||||||
|
STRACE(("AppServer received unexpected code %" B_PRId32 "\n",
|
||||||
|
message->what));
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
bool
|
||||||
|
AppServer::QuitRequested()
|
||||||
|
{
|
||||||
|
#if TEST_MODE
|
||||||
|
while (fDesktops.CountItems() > 0) {
|
||||||
|
Desktop *desktop = fDesktops.RemoveItemAt(0);
|
||||||
|
|
||||||
|
thread_id thread = desktop->Thread();
|
||||||
|
desktop->PostMessage(B_QUIT_REQUESTED);
|
||||||
|
|
||||||
|
// we just wait for the desktop to kill itself
|
||||||
|
status_t status;
|
||||||
|
wait_for_thread(thread, &status);
|
||||||
|
}
|
||||||
|
|
||||||
|
return BServer::QuitRequested();
|
||||||
|
#else
|
||||||
|
return false;
|
||||||
|
#endif
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -160,112 +209,18 @@ AppServer::_FindDesktop(uid_t userID, const char* targetScreen)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*! \brief Message handling function for all messages sent to the app_server
|
|
||||||
\param code ID of the message sent
|
|
||||||
\param buffer Attachment buffer for the message.
|
|
||||||
|
|
||||||
*/
|
|
||||||
void
|
|
||||||
AppServer::_DispatchMessage(int32 code, BPrivate::LinkReceiver& msg)
|
|
||||||
{
|
|
||||||
switch (code) {
|
|
||||||
case AS_GET_DESKTOP:
|
|
||||||
{
|
|
||||||
Desktop* desktop = NULL;
|
|
||||||
|
|
||||||
port_id replyPort;
|
|
||||||
msg.Read<port_id>(&replyPort);
|
|
||||||
|
|
||||||
int32 userID;
|
|
||||||
msg.Read<int32>(&userID);
|
|
||||||
|
|
||||||
char* targetScreen = NULL;
|
|
||||||
msg.ReadString(&targetScreen);
|
|
||||||
if (targetScreen != NULL && strlen(targetScreen) == 0) {
|
|
||||||
free(targetScreen);
|
|
||||||
targetScreen = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
int32 version;
|
|
||||||
if (msg.Read<int32>(&version) < B_OK
|
|
||||||
|| version != AS_PROTOCOL_VERSION) {
|
|
||||||
syslog(LOG_ERR, "Application for user %" B_PRId32 " with port "
|
|
||||||
"%" B_PRId32 " does not support the current server "
|
|
||||||
"protocol.\n", userID, replyPort);
|
|
||||||
} else {
|
|
||||||
desktop = _FindDesktop(userID, targetScreen);
|
|
||||||
if (desktop == NULL) {
|
|
||||||
// we need to create a new desktop object for this user
|
|
||||||
// TODO: test if the user exists on the system
|
|
||||||
// TODO: maybe have a separate AS_START_DESKTOP_SESSION for
|
|
||||||
// authorizing the user
|
|
||||||
desktop = _CreateDesktop(userID, targetScreen);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
free(targetScreen);
|
|
||||||
|
|
||||||
BPrivate::LinkSender reply(replyPort);
|
|
||||||
if (desktop != NULL) {
|
|
||||||
reply.StartMessage(B_OK);
|
|
||||||
reply.Attach<port_id>(desktop->MessagePort());
|
|
||||||
} else
|
|
||||||
reply.StartMessage(B_ERROR);
|
|
||||||
|
|
||||||
reply.Flush();
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
#if TEST_MODE
|
|
||||||
case B_QUIT_REQUESTED:
|
|
||||||
{
|
|
||||||
// We've been asked to quit, so (for now) broadcast to all
|
|
||||||
// desktops to quit. This situation will occur only when the server
|
|
||||||
// is compiled as a regular Be application.
|
|
||||||
|
|
||||||
fQuitting = true;
|
|
||||||
|
|
||||||
while (fDesktops.CountItems() > 0) {
|
|
||||||
Desktop *desktop = fDesktops.RemoveItemAt(0);
|
|
||||||
|
|
||||||
thread_id thread = desktop->Thread();
|
|
||||||
desktop->PostMessage(B_QUIT_REQUESTED);
|
|
||||||
|
|
||||||
// we just wait for the desktop to kill itself
|
|
||||||
status_t status;
|
|
||||||
wait_for_thread(thread, &status);
|
|
||||||
}
|
|
||||||
|
|
||||||
delete this;
|
|
||||||
|
|
||||||
// we are now clear to exit
|
|
||||||
exit(0);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
default:
|
|
||||||
STRACE(("Server::MainLoop received unexpected code %" B_PRId32 " "
|
|
||||||
"(offset %" B_PRId32 ")\n", code, code - SERVER_TRUE));
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// #pragma mark -
|
// #pragma mark -
|
||||||
|
|
||||||
|
|
||||||
int
|
int
|
||||||
main(int argc, char** argv)
|
main(int argc, char** argv)
|
||||||
{
|
{
|
||||||
// There can be only one....
|
|
||||||
if (find_port(SERVER_PORT_NAME) >= B_OK)
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
srand(real_time_clock_usecs());
|
srand(real_time_clock_usecs());
|
||||||
|
|
||||||
AppServer* server = new AppServer;
|
status_t status;
|
||||||
server->RunLooper();
|
AppServer* server = new AppServer(&status);
|
||||||
|
if (status == B_OK)
|
||||||
|
server->Run();
|
||||||
|
|
||||||
return 0;
|
return status == B_OK ? EXIT_SUCCESS : EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
|
|||||||
+25
-31
@@ -1,58 +1,52 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2001-2011, Haiku, Inc.
|
* Copyright 2001-2015, Haiku, Inc.
|
||||||
* Distributed under the terms of the MIT license.
|
* Distributed under the terms of the MIT license.
|
||||||
*
|
*
|
||||||
* Authors:
|
* Authors:
|
||||||
* DarkWyrm <[email protected]>
|
* DarkWyrm <[email protected]>
|
||||||
|
* Axel Dörfler, [email protected]
|
||||||
*/
|
*/
|
||||||
#ifndef APP_SERVER_H
|
#ifndef APP_SERVER_H
|
||||||
#define APP_SERVER_H
|
#define APP_SERVER_H
|
||||||
|
|
||||||
|
|
||||||
#include <OS.h>
|
|
||||||
#include <Locker.h>
|
|
||||||
#include <List.h>
|
|
||||||
#include <Application.h>
|
#include <Application.h>
|
||||||
#include <Window.h>
|
#include <List.h>
|
||||||
#include <String.h>
|
#include <Locker.h>
|
||||||
#include <ObjectList.h>
|
#include <ObjectList.h>
|
||||||
#include <TokenSpace.h>
|
#include <OS.h>
|
||||||
|
#include <Server.h>
|
||||||
|
#include <String.h>
|
||||||
|
#include <Window.h>
|
||||||
|
|
||||||
#include "ServerConfig.h"
|
|
||||||
#include "MessageLooper.h"
|
#include "MessageLooper.h"
|
||||||
|
#include "ServerConfig.h"
|
||||||
|
|
||||||
|
|
||||||
class ServerApp;
|
class ServerApp;
|
||||||
class BitmapManager;
|
class BitmapManager;
|
||||||
class Desktop;
|
class Desktop;
|
||||||
|
|
||||||
using BPrivate::BTokenSpace;
|
|
||||||
|
|
||||||
namespace BPrivate {
|
class AppServer : public BServer {
|
||||||
class PortLink;
|
public:
|
||||||
};
|
AppServer(status_t* status);
|
||||||
|
virtual ~AppServer();
|
||||||
|
|
||||||
|
virtual void MessageReceived(BMessage* message);
|
||||||
|
virtual bool QuitRequested();
|
||||||
|
|
||||||
class AppServer : public MessageLooper {
|
private:
|
||||||
public:
|
Desktop* _CreateDesktop(uid_t userID,
|
||||||
AppServer();
|
const char* targetScreen);
|
||||||
virtual ~AppServer();
|
Desktop* _FindDesktop(uid_t userID,
|
||||||
|
const char* targetScreen);
|
||||||
|
|
||||||
void RunLooper();
|
void _LaunchInputServer();
|
||||||
virtual port_id MessagePort() const { return fMessagePort; }
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
virtual void _DispatchMessage(int32 code, BPrivate::LinkReceiver& link);
|
BObjectList<Desktop> fDesktops;
|
||||||
|
BLocker fDesktopLock;
|
||||||
Desktop* _CreateDesktop(uid_t userID, const char* targetScreen);
|
|
||||||
Desktop* _FindDesktop(uid_t userID, const char* targetScreen);
|
|
||||||
|
|
||||||
void _LaunchInputServer();
|
|
||||||
|
|
||||||
private:
|
|
||||||
port_id fMessagePort;
|
|
||||||
|
|
||||||
BObjectList<Desktop> fDesktops;
|
|
||||||
BLocker fDesktopLock;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user