< prev index next >

src/jdk.jpackage/linux/native/libapplauncher/LinuxPlatform.cpp

Print this page

        

@@ -23,50 +23,68 @@
  * questions.
  */
 
 #include "Platform.h"
 
-#ifdef LINUX
-
 #include "JavaVirtualMachine.h"
 #include "LinuxPlatform.h"
 #include "PlatformString.h"
 #include "IniFile.h"
 #include "Helpers.h"
+#include "FilePath.h"
 
 #include <stdlib.h>
 #include <pwd.h>
 #include <sys/file.h>
 #include <sys/stat.h>
 #include <errno.h>
 #include <unistd.h>
 #include <sys/types.h>
 #include <limits.h>
+#include <signal.h>
 
 #define LINUX_JPACKAGE_TMP_DIR "/.java/jpackage/tmp"
 
-
 TString GetEnv(const TString &name) {
     TString result;
 
-    char *value = ::getenv((TCHAR*)name.c_str());
+    char *value = ::getenv((TCHAR*) name.c_str());
 
     if (value != NULL) {
        result = value;
     }
 
     return result;
 }
 
 LinuxPlatform::LinuxPlatform(void) : Platform(),
-        GenericPlatform(), PosixPlatform() {
+PosixPlatform() {
     FMainThread = pthread_self();
 }
 
 LinuxPlatform::~LinuxPlatform(void) {
 }
 
+TString LinuxPlatform::GetPackageAppDirectory() {
+    return FilePath::IncludeTrailingSeparator(
+            GetPackageRootDirectory()) + _T("app");
+}
+
+TString LinuxPlatform::GetAppName() {
+    TString result = GetModuleFileName();
+    result = FilePath::ExtractFileName(result);
+    return result;
+}
+
+TString LinuxPlatform::GetPackageLauncherDirectory() {
+    return GetPackageRootDirectory();
+}
+
+TString LinuxPlatform::GetPackageRuntimeBinDirectory() {
+    return FilePath::IncludeTrailingSeparator(GetPackageRootDirectory()) + _T("runtime/bin");
+}
+
 void LinuxPlatform::ShowMessage(TString title, TString description) {
     printf("%s %s\n", PlatformString(title).toPlatformString(),
             PlatformString(description).toPlatformString());
     fflush(stdout);
 }

@@ -172,30 +190,94 @@
     TPlatformNumber result = pages * page_size;
     result = result / 1048576; // Convert from bytes to megabytes.
     return result;
 }
 
-#ifdef DEBUG
-bool LinuxPlatform::IsNativeDebuggerPresent() {
-    // gdb opens file descriptors stdin=3, stdout=4, stderr=5 whereas
-    // a typical prog uses only stdin=0, stdout=1, stderr=2.
+void PosixProcess::Cleanup() {
+    if (FOutputHandle != 0) {
+        close(FOutputHandle);
+        FOutputHandle = 0;
+    }
+
+    if (FInputHandle != 0) {
+        close(FInputHandle);
+        FInputHandle = 0;
+    }
+}
+
+#define PIPE_READ 0
+#define PIPE_WRITE 1
+
+bool PosixProcess::Execute(const TString Application,
+        const std::vector<TString> Arguments, bool AWait) {
     bool result = false;
-    FILE *fd = fopen("/tmp", "r");
 
-    if (fileno(fd) > 5) {
+    if (FRunning == false) {
+        FRunning = true;
+
+        int handles[2];
+
+        if (pipe(handles) == -1) {
+            return false;
+        }
+
+        struct sigaction sa;
+        sa.sa_handler = SIG_IGN;
+        sigemptyset(&sa.sa_mask);
+        sa.sa_flags = 0;
+
+        FChildPID = fork();
+
+        // PID returned by vfork is 0 for the child process and the
+        // PID of the child process for the parent.
+        if (FChildPID == -1) {
+            // Error
+            TString message = PlatformString::Format(
+                    _T("Error: Unable to create process %s"),
+                    Application.data());
+            throw Exception(message);
+        } else if (FChildPID == 0) {
+            Cleanup();
+            TString command = Application;
+
+            for (std::vector<TString>::const_iterator iterator =
+                    Arguments.begin(); iterator != Arguments.end();
+                    iterator++) {
+                command += TString(_T(" ")) + *iterator;
+            }
+#ifdef DEBUG
+            printf("%s\n", command.data());
+#endif // DEBUG
+
+            dup2(handles[PIPE_READ], STDIN_FILENO);
+            dup2(handles[PIPE_WRITE], STDOUT_FILENO);
+
+            close(handles[PIPE_READ]);
+            close(handles[PIPE_WRITE]);
+
+            execl("/bin/sh", "sh", "-c", command.data(), (char *) 0);
+
+            _exit(127);
+        } else {
+            FOutputHandle = handles[PIPE_READ];
+            FInputHandle = handles[PIPE_WRITE];
+
+            if (AWait == true) {
+                ReadOutput();
+                Wait();
+                Cleanup();
+                FRunning = false;
         result = true;
+            } else {
+                result = true;
+            }
+        }
     }
 
-    fclose(fd);
     return result;
 }
 
-int LinuxPlatform::GetProcessID() {
-    int pid = getpid();
-    return pid;
-}
-#endif //DEBUG
 
 //----------------------------------------------------------------------------
 
 #ifndef __UNIX_JPACKAGE_PLATFORM__
 #define __UNIX_JPACKAGE_PLATFORM__

@@ -227,10 +309,11 @@
 
 #define JPACKAGE_STRDUP(strSource) \
     strdup((strSource))
 
 //return "error code" (like on Windows)
+
 static int JPACKAGE_STRNCPY(char *strDest, size_t numberOfElements,
         const char *strSource, size_t count) {
     char *s = strncpy(strDest, strSource, count);
     // Duplicate behavior of the Windows' _tcsncpy_s() by adding a NULL
     // terminator at the end of the string.

@@ -336,28 +419,26 @@
     XMLAttribute* _next;        // Next attribute for this tag
 };
 
 // Public interface
 static void     RemoveNonAsciiUTF8FromBuffer(char *buf);
-XMLNode* ParseXMLDocument    (TCHAR* buf);
-void     FreeXMLDocument     (XMLNode* root);
+XMLNode* ParseXMLDocument(TCHAR* buf);
+void FreeXMLDocument(XMLNode* root);
 
 // Utility methods for parsing document
-XMLNode* FindXMLChild        (XMLNode* root,      const TCHAR* name);
-TCHAR*    FindXMLAttribute    (XMLAttribute* attr, const TCHAR* name);
+XMLNode* FindXMLChild(XMLNode* root, const TCHAR* name);
+TCHAR* FindXMLAttribute(XMLAttribute* attr, const TCHAR* name);
 
 // Debugging
 void PrintXMLDocument(XMLNode* node, int indt);
 
-
 #include <sys/types.h>
 #include <sys/stat.h>
 #include <setjmp.h>
 #include <stdlib.h>
 #include <wctype.h>
 
-
 #define JWS_assert(s, msg)      \
     if (!(s)) { Abort(msg); }
 
 
 // Internal declarations

@@ -455,51 +536,51 @@
     char* q;
     char c;
     p = q = buf;
     // We are not using NEXT_CHAR() to check if *q is NULL, as q is output
     // location and offset for q is smaller than for p.
-    while(*p != '\0') {
+    while (*p != '\0') {
         c = *p;
-        if ( (c & 0x80) == 0) {
+        if ((c & 0x80) == 0) {
             /* Range A */
             *q++ = *p;
             NEXT_CHAR(p);
-        } else if ((c & 0xE0) == 0xC0){
+        } else if ((c & 0xE0) == 0xC0) {
             /* Range B */
-            *q++ = (char)0xFF;
+            *q++ = (char) 0xFF;
             NEXT_CHAR(p);
             NEXT_CHAR_OR_BREAK(p);
         } else {
             /* Range C */
-            *q++ = (char)0xFF;
+            *q++ = (char) 0xFF;
             NEXT_CHAR(p);
             SKIP_CHARS_OR_BREAK(p, 2);
         }
     }
     /* Null terminate string */
     *q = '\0';
 }
 
 static TCHAR* SkipWhiteSpace(TCHAR *p) {
     if (p != NULL) {
-        while(iswspace(*p))
+        while (iswspace(*p))
             NEXT_CHAR_OR_BREAK(p);
     }
     return p;
 }
 
 static TCHAR* SkipXMLName(TCHAR *p) {
     TCHAR c = *p;
     /* Check if start of token */
-    if ( ('a' <= c && c <= 'z') ||
+    if (('a' <= c && c <= 'z') ||
          ('A' <= c && c <= 'Z') ||
          c == '_' || c == ':') {
 
-        while( ('a' <= c && c <= 'z') ||
+        while (('a' <= c && c <= 'z') ||
                ('A' <= c && c <= 'Z') ||
                ('0' <= c && c <= '9') ||
-               c == '_' || c == ':' || c == '.' || c == '-' ) {
+                c == '_' || c == ':' || c == '.' || c == '-') {
             NEXT_CHAR(p);
             c = *p;
             if (c == '\0') break;
         }
     }

@@ -514,11 +595,11 @@
                 if (JPACKAGE_STRNCMP(p, _T("-->"), 3) == 0) {
                     SKIP_CHARS(p, 3);
                     return p;
                 }
                 NEXT_CHAR(p);
-            } while(*p != '\0');
+            } while (*p != '\0');
         }
     }
     return p;
 }
 

@@ -546,11 +627,11 @@
                 if (JPACKAGE_STRNCMP(p, _T("?>"), 2) == 0) {
                     SKIP_CHARS(p, 2);
                     return p;
                 }
                 NEXT_CHAR(p);
-            } while(*p != '\0');
+            } while (*p != '\0');
         }
     }
     return p;
 }
 

@@ -561,16 +642,16 @@
 static void ConvertBuiltInEntities(TCHAR* p) {
     TCHAR* q;
     q = p;
     // We are not using NEXT_CHAR() to check if *q is NULL,
     // as q is output location and offset for q is smaller than for p.
-    while(*p) {
+    while (*p) {
         if (IsPCData(p)) {
             /* dont convert &xxx values within PData */
             TCHAR *end;
             end = SkipPCData(p);
-            while(p < end) {
+            while (p < end) {
                 *q++ = *p;
                 NEXT_CHAR(p);
             }
         } else {
             if (JPACKAGE_STRNCMP(p, _T("&amp;"), 5) == 0) {

@@ -617,12 +698,12 @@
 /* Copy token from buffer to Token variable */
 static void SetToken(int type, TCHAR* start, TCHAR* end) {
     int len = end - start;
     if (len > MaxTokenSize) {
         if (CurTokenName != NULL) free(CurTokenName);
-        CurTokenName = (TCHAR *)malloc((len + 1) * sizeof(TCHAR));
-        if (CurTokenName == NULL ) {
+        CurTokenName = (TCHAR *) malloc((len + 1) * sizeof (TCHAR));
+        if (CurTokenName == NULL) {
             return;
         }
         MaxTokenSize = len;
     }
 

@@ -640,19 +721,19 @@
         q = CurPos;
         CurPos = SkipWhiteSpace(CurPos);
         CurPos = SkipXMLComment(CurPos); /* Must be called befor DocTypes */
         CurPos = SkipXMLDocType(CurPos); /* <! ... > directives */
         CurPos = SkipXMLProlog(CurPos);   /* <? ... ?> directives */
-    } while(CurPos != q);
+    } while (CurPos != q);
 
     return CurPos;
 }
 
 /* Parses next token and initializes the global token variables above
    The tokennizer automatically skips comments (<!-- comment -->) and
    <! ... > directives.
-*/
+ */
 static void GetNextToken(void) {
     TCHAR *p, *q;
 
     /* Skip white space and comment sections */
     p = SkipFilling();

@@ -677,11 +758,11 @@
         CurTokenType = TOKEN_EMPTY_CLOSE_BRACKET;
         SKIP_CHARS(p, 2);
     } else {
         /* Search for end of data */
         q = p + 1;
-        while(*q && *q != '<') {
+        while (*q && *q != '<') {
             if (IsPCData(q)) {
                 q = SkipPCData(q);
             } else {
                 NEXT_CHAR(q);
             }

@@ -695,11 +776,11 @@
     CurPos = p;
 }
 
 static XMLNode* CreateXMLNode(int type, TCHAR* name) {
     XMLNode* node;
-    node  = (XMLNode*)malloc(sizeof(XMLNode));
+    node = (XMLNode*) malloc(sizeof (XMLNode));
     if (node == NULL) {
         return NULL;
     }
     node->_type = type;
     node->_name = name;

@@ -709,11 +790,11 @@
     return node;
 }
 
 static XMLAttribute* CreateXMLAttribute(TCHAR *name, TCHAR* value) {
     XMLAttribute* attr;
-    attr = (XMLAttribute*)malloc(sizeof(XMLAttribute));
+    attr = (XMLAttribute*) malloc(sizeof (XMLAttribute));
     if (attr == NULL) {
         return NULL;
     }
     attr->_name = name;
     attr->_value = value;

@@ -722,12 +803,11 @@
 }
 
 XMLNode* ParseXMLDocument(TCHAR* buf) {
     XMLNode* root;
     int err_code = setjmp(jmpbuf);
-    switch (err_code)
-    {
+    switch (err_code) {
     case JMP_NO_ERROR:
 #ifndef _UNICODE
         /* Remove UTF-8 encoding from buffer */
         RemoveNonAsciiUTF8FromBuffer(buf);
 #endif

@@ -744,11 +824,11 @@
         if (root_node != NULL) {
             FreeXMLDocument(root_node);
             root_node = NULL;
         }
         if (CurTokenName != NULL) free(CurTokenName);
-        fprintf(stderr,"Error during parsing jnlp file...\n");
+            fprintf(stderr, "Error during parsing jnlp file...\n");
         exit(-1);
     break;
     default:
         root = NULL;
     break;

@@ -767,17 +847,17 @@
 
         /* Create node for new element tag */
         node = CreateXMLNode(xmlTagType, JPACKAGE_STRDUP(CurTokenName));
         /* We need to save root node pointer to be able to cleanup
            if an error happens during parsing */
-        if(!root_node) {
+        if (!root_node) {
             root_node = node;
         }
         /* Parse attributes. This section eats a all input until
            EOF, a > or a /> */
         attr = ParseXMLAttribute();
-        while(attr != NULL) {
+        while (attr != NULL) {
           attr->_next = node->_attributes;
           node->_attributes = attr;
           attr = ParseXMLAttribute();
         }
 

@@ -785,16 +865,16 @@
          * TOKEN_EMPTY_CLOSE_BRACKET */
         GetNextToken();
 
         /* Skip until '>', '/>' or EOF. This should really be an error, */
         /* but we are loose */
-//        if(CurTokenType == TOKEN_EMPTY_CLOSE_BRACKET ||
-//               CurTokenType == TOKEN_CLOSE_BRACKET ||
-//               CurTokenType  == TOKEN_EOF) {
-//            println("XML Parsing error: wrong kind of token found");
-//            return NULL;
-//        }
+        //        if(CurTokenType == TOKEN_EMPTY_CLOSE_BRACKET ||
+        //               CurTokenType == TOKEN_CLOSE_BRACKET ||
+        //               CurTokenType  == TOKEN_EOF) {
+        //            println("XML Parsing error: wrong kind of token found");
+        //            return NULL;
+        //        }
 
         if (CurTokenType == TOKEN_EMPTY_CLOSE_BRACKET) {
             GetNextToken();
             /* We are done with the sublevel - fall through to continue */
             /* parsing tags at the same level */

@@ -806,11 +886,11 @@
 
             if (CurTokenType == TOKEN_END_TAG) {
                 /* Find closing bracket '>' for end tag */
                 do {
                    GetNextToken();
-                } while(CurTokenType != TOKEN_EOF &&
+                } while (CurTokenType != TOKEN_EOF &&
                         CurTokenType != TOKEN_CLOSE_BRACKET);
                 GetNextToken();
             }
         }
 

@@ -824,11 +904,11 @@
     } else if (CurTokenType == TOKEN_PCDATA) {
         /* Create node for pcdata */
         node = CreateXMLNode(xmlPCDataType, JPACKAGE_STRDUP(CurTokenName));
         /* We need to save root node pointer to be able to cleanup
            if an error happens during parsing */
-        if(!root_node) {
+        if (!root_node) {
             root_node = node;
         }
         GetNextToken();
         return node;
     }

@@ -841,12 +921,11 @@
 static XMLAttribute* ParseXMLAttribute(void) {
     TCHAR* q = NULL;
     TCHAR* name = NULL;
     TCHAR* PrevPos = NULL;
 
-    do
-    {
+    do {
         /* We need to check this condition to avoid endless loop
            in case if an error happend during parsing. */
         if (PrevPos == CurPos) {
             if (name != NULL) {
                 free(name);

@@ -874,11 +953,11 @@
             return NULL;
         }
 
         /* Find end of name */
         q = CurPos;
-        while(*q && !iswspace(*q) && *q !='=') NEXT_CHAR(q);
+        while (*q && !iswspace(*q) && *q != '=') NEXT_CHAR(q);
 
         SetToken(TOKEN_UNKNOWN, CurPos, q);
         if (name) {
             free(name);
             name = NULL;

@@ -892,24 +971,24 @@
         /* Next TCHARacter must be '=' for a valid attribute.
            If it is not, this is really an error.
            We ignore this, and just try to parse an attribute
            out of the rest of the string.
         */
-    } while(*CurPos != '=');
+    } while (*CurPos != '=');
 
     NEXT_CHAR(CurPos);
     CurPos = SkipWhiteSpace(CurPos);
     /* Parse CDATA part of attribute */
     if ((*CurPos == '\"') || (*CurPos == '\'')) {
         TCHAR quoteChar = *CurPos;
         q = ++CurPos;
-        while(*q != '\0' && *q != quoteChar) NEXT_CHAR(q);
+        while (*q != '\0' && *q != quoteChar) NEXT_CHAR(q);
         SetToken(TOKEN_CDATA, CurPos, q);
         CurPos = q + 1;
     } else {
         q = CurPos;
-        while(*q != '\0' && !iswspace(*q)) NEXT_CHAR(q);
+        while (*q != '\0' && !iswspace(*q)) NEXT_CHAR(q);
         SetToken(TOKEN_CDATA, CurPos, q);
         CurPos = q;
     }
 
     //Note: no need to free name and CurTokenName duplicate; they're assigned

@@ -953,11 +1032,10 @@
     if (attr == NULL) return NULL;
     if (JPACKAGE_STRCMP(attr->_name, name) == 0) return attr->_value;
     return FindXMLAttribute(attr->_next, name);
 }
 
-
 void PrintXMLDocument(XMLNode* node, int indt) {
     if (node == NULL) return;
 
     if (node->_type == xmlTagType) {
         JPACKAGE_PRINTF(_T("\n"));

@@ -985,197 +1063,25 @@
     PrintXMLAttributes(attr->_next);
 }
 
 static void indent(int indt) {
     int i;
-    for(i = 0; i < indt; i++) {
+    for (i = 0; i < indt; i++) {
         JPACKAGE_PRINTF(_T("  "));
     }
 }
 
 const TCHAR *CDStart = _T("<![CDATA[");
 const TCHAR *CDEnd = _T("]]>");
 
-
 static TCHAR* SkipPCData(TCHAR *p) {
     TCHAR *end = JPACKAGE_STRSTR(p, CDEnd);
     if (end != NULL) {
-        return end+sizeof(CDEnd);
+        return end + sizeof (CDEnd);
     }
     return (++p);
 }
 
 static int IsPCData(TCHAR *p) {
-    const int size = sizeof(CDStart);
+    const int size = sizeof (CDStart);
     return (JPACKAGE_STRNCMP(CDStart, p, size) == 0);
 }
-
-namespace {
-    template<class funcType>
-    class DllFunction {
-        const Library& lib;
-        funcType funcPtr;
-        std::string theName;
-
-    public:
-        DllFunction(const Library& library,
-                const std::string &funcName): lib(library) {
-            funcPtr = reinterpret_cast<funcType>(lib.GetProcAddress(funcName));
-            if (!funcPtr) {
-                throw std::runtime_error("Failed to load function \""
-                        + funcName + "\" from \""
-                        + library.GetName() + "\" library");
-            }
-        }
-
-        operator funcType() const {
-            return funcPtr;
-        }
-    };
-} // namespace
-
-extern "C" {
-typedef Status (*XInitThreadsFuncPtr)();
-typedef Display* (*XOpenDisplayFuncPtr)(char *display_name);
-
-typedef Atom (*XInternAtomFuncPtr)(
-        Display *display, char *atom_name, Bool only_if_exists);
-
-typedef Window (*XDefaultRootWindowFuncPtr)(Display *display);
-
-typedef int (*XCloseDisplayFuncPtr)(Display *display);
-}
-
-ProcessReactivator::ProcessReactivator(pid_t pid): _pid(pid) {
-    const std::string libname = "libX11.so";
-    if(!libX11.Load(libname)) {
-        throw std::runtime_error("Failed to load \"" + libname + "\" library");
-    }
-
-    DllFunction<XInitThreadsFuncPtr> XInitThreadsFunc(libX11, "XInitThreads");
-
-    XInitThreadsFunc();
-
-    DllFunction<XOpenDisplayFuncPtr> XOpenDisplayFunc(libX11, "XOpenDisplay");
-
-    _display = XOpenDisplayFunc(NULL);
-
-    DllFunction<XInternAtomFuncPtr> XInternAtomFunc(libX11, "XInternAtom");
-
-    _atomPid = XInternAtomFunc(_display, (char*)"_NET_WM_PID", True);
-
-    if (_atomPid == None) {
-        return;
-    }
-
-    DllFunction<XDefaultRootWindowFuncPtr> XDefaultRootWindowFunc(libX11,
-            "XDefaultRootWindow");
-
-    searchWindowHelper(XDefaultRootWindowFunc(_display));
-
-    reactivateProcess();
-
-    DllFunction<XCloseDisplayFuncPtr> XCloseDisplayFunc(libX11,
-            "XCloseDisplay");
-
-    XCloseDisplayFunc(_display);
-}
-
-extern "C" {
-typedef int (*XGetWindowPropertyFuncPtr)(
-        Display *display, Window w, Atom property, long long_offset,
-        long long_length, Bool d, Atom req_type, Atom *actual_type_return,
-        int *actual_format_return, unsigned long *nitems_return,
-        unsigned long *bytes_after_return, unsigned char **prop_return);
-
-typedef Status (*XQueryTreeFuncPtr)(
-        Display *display, Window w, Window *root_return, Window *parent_return,
-         Window **children_return, unsigned int *nchildren_return);
-
-typedef int (*XFreeFuncPtr)(void *data);
-}
-
-void ProcessReactivator::searchWindowHelper(Window w) {
-
-    DllFunction<XGetWindowPropertyFuncPtr> XGetWindowPropertyFunc(libX11,
-            "XGetWindowProperty");
-
-    DllFunction<XFreeFuncPtr> XFreeFunc(libX11, "XFree");
-
-    Atom type;
-    int format;
-    unsigned long  num, bytesAfter;
-    unsigned char* propPid = 0;
-    if (Success == XGetWindowPropertyFunc(_display, w, _atomPid, 0, 1,
-            False, XA_CARDINAL, &type, &format, &num, &bytesAfter, &propPid)) {
-        if (propPid != 0) {
-            if (_pid == *((pid_t *)propPid)) {
-                _result.push_back(w);
-            }
-            XFreeFunc(propPid);
-        }
-    }
-
-    DllFunction<XQueryTreeFuncPtr> XQueryTreeFunc(libX11, "XQueryTree");
-
-    Window root, parent;
-    Window* child;
-    unsigned int numChildren;
-    if (0 != XQueryTreeFunc(_display, w, &root,
-            &parent, &child, &numChildren)) {
-        for (unsigned int i = 0; i < numChildren; i++) {
-            searchWindowHelper(child[i]);
-        }
-    }
-}
-
-
-extern "C" {
-typedef Status (*XGetWindowAttributesFuncPtr)(Display *display, Window w,
-        XWindowAttributes *window_attributes_return);
-
-typedef Status (*XSendEventFuncPtr)(Display *display, Window w, Bool propagate,
-        long event_mask, XEvent *event_send);
-
-typedef int (*XRaiseWindowFuncPtr)(Display *display, Window w);
-}
-
-void ProcessReactivator::reactivateProcess() {
-
-    DllFunction<XGetWindowAttributesFuncPtr> XGetWindowAttributesFunc(libX11,
-            "XGetWindowAttributes");
-
-    DllFunction<XSendEventFuncPtr> XSendEventFunc(libX11, "XSendEvent");
-
-    DllFunction<XRaiseWindowFuncPtr> XRaiseWindowFunc(libX11, "XRaiseWindow");
-
-    DllFunction<XInternAtomFuncPtr> XInternAtomFunc(libX11, "XInternAtom");
-
-    for (std::list<Window>::const_iterator it = _result.begin();
-            it != _result.end(); it++) {
-        // try sending an event to activate window,
-        // after that we can try to raise it.
-        XEvent xev;
-        Atom atom = XInternAtomFunc (
-                _display, (char*)"_NET_ACTIVE_WINDOW", False);
-        xev.xclient.type = ClientMessage;
-        xev.xclient.serial = 0;
-        xev.xclient.send_event = True;
-        xev.xclient.display = _display;
-        xev.xclient.window = *it;
-        xev.xclient.message_type = atom;
-        xev.xclient.format = 32;
-        xev.xclient.data.l[0] = 2;
-        xev.xclient.data.l[1] = 0;
-        xev.xclient.data.l[2] = 0;
-        xev.xclient.data.l[3] = 0;
-        xev.xclient.data.l[4] = 0;
-        XWindowAttributes attr;
-        XGetWindowAttributesFunc(_display, *it, &attr);
-        XSendEventFunc(_display, attr.root, False,
-            SubstructureRedirectMask | SubstructureNotifyMask, &xev);
-        XRaiseWindowFunc(_display, *it);
-    }
-}
-
-
-#endif // LINUX
< prev index next >