xref: /aoo42x/main/vcl/unx/kde/kdedata.cxx (revision 288dd0d8)
19f62ea84SAndrew Rist /**************************************************************
2cdf0e10cSrcweir  *
39f62ea84SAndrew Rist  * Licensed to the Apache Software Foundation (ASF) under one
49f62ea84SAndrew Rist  * or more contributor license agreements.  See the NOTICE file
59f62ea84SAndrew Rist  * distributed with this work for additional information
69f62ea84SAndrew Rist  * regarding copyright ownership.  The ASF licenses this file
79f62ea84SAndrew Rist  * to you under the Apache License, Version 2.0 (the
89f62ea84SAndrew Rist  * "License"); you may not use this file except in compliance
99f62ea84SAndrew Rist  * with the License.  You may obtain a copy of the License at
109f62ea84SAndrew Rist  *
119f62ea84SAndrew Rist  *   http://www.apache.org/licenses/LICENSE-2.0
129f62ea84SAndrew Rist  *
139f62ea84SAndrew Rist  * Unless required by applicable law or agreed to in writing,
149f62ea84SAndrew Rist  * software distributed under the License is distributed on an
159f62ea84SAndrew Rist  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
169f62ea84SAndrew Rist  * KIND, either express or implied.  See the License for the
179f62ea84SAndrew Rist  * specific language governing permissions and limitations
189f62ea84SAndrew Rist  * under the License.
199f62ea84SAndrew Rist  *
209f62ea84SAndrew Rist  *************************************************************/
219f62ea84SAndrew Rist 
229f62ea84SAndrew Rist 
23cdf0e10cSrcweir 
24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove
25cdf0e10cSrcweir #include "precompiled_vcl.hxx"
26cdf0e10cSrcweir 
27cdf0e10cSrcweir #define _SV_SALDATA_CXX
28cdf0e10cSrcweir #include <shell/kde_headers.h>
29cdf0e10cSrcweir 
30cdf0e10cSrcweir #include <unistd.h>
31cdf0e10cSrcweir #include <fcntl.h>
32cdf0e10cSrcweir 
33cdf0e10cSrcweir #include <stdio.h>
34cdf0e10cSrcweir #include <string.h>
35cdf0e10cSrcweir #include <stdlib.h>
36cdf0e10cSrcweir #include <limits.h>
37cdf0e10cSrcweir #include <errno.h>
38cdf0e10cSrcweir #include <poll.h>
39cdf0e10cSrcweir #ifdef FREEBSD
40cdf0e10cSrcweir #include <sys/types.h>
41cdf0e10cSrcweir #include <sys/time.h>
42cdf0e10cSrcweir #include <unistd.h>
43cdf0e10cSrcweir #endif
44cdf0e10cSrcweir 
45cdf0e10cSrcweir #include <osl/thread.h>
46cdf0e10cSrcweir #include <osl/process.h>
47cdf0e10cSrcweir #include <osl/module.h>
48cdf0e10cSrcweir 
49cdf0e10cSrcweir #include <tools/debug.hxx>
50cdf0e10cSrcweir 
51cdf0e10cSrcweir #include <vos/process.hxx>
52cdf0e10cSrcweir #include <vos/mutex.hxx>
53cdf0e10cSrcweir 
54cdf0e10cSrcweir #include "unx/kde/kdedata.hxx"
55cdf0e10cSrcweir #include "unx/i18n_im.hxx"
56cdf0e10cSrcweir #include "unx/i18n_xkb.hxx"
57cdf0e10cSrcweir 
58cdf0e10cSrcweir #include "vclpluginapi.h"
59cdf0e10cSrcweir 
60cdf0e10cSrcweir /* #i59042# override KApplications method for session management
61cdf0e10cSrcweir  * since it will interfere badly with our own.
62cdf0e10cSrcweir  */
63cdf0e10cSrcweir class VCLKDEApplication : public KApplication
64cdf0e10cSrcweir {
65cdf0e10cSrcweir     public:
66cdf0e10cSrcweir     VCLKDEApplication() : KApplication() {}
67cdf0e10cSrcweir 
68cdf0e10cSrcweir     virtual void commitData(QSessionManager &sm);
69cdf0e10cSrcweir };
70cdf0e10cSrcweir 
71cdf0e10cSrcweir void VCLKDEApplication::commitData(QSessionManager&)
72cdf0e10cSrcweir {
73cdf0e10cSrcweir }
74cdf0e10cSrcweir 
75cdf0e10cSrcweir /***************************************************************************
76cdf0e10cSrcweir  * class SalKDEDisplay                                                     *
77cdf0e10cSrcweir  ***************************************************************************/
78cdf0e10cSrcweir 
79cdf0e10cSrcweir SalKDEDisplay::SalKDEDisplay( Display* pDisp )
80cdf0e10cSrcweir     : SalX11Display( pDisp )
81cdf0e10cSrcweir {
82cdf0e10cSrcweir }
83cdf0e10cSrcweir 
84cdf0e10cSrcweir SalKDEDisplay::~SalKDEDisplay()
85cdf0e10cSrcweir {
86cdf0e10cSrcweir     // in case never a frame opened
87cdf0e10cSrcweir     static_cast<KDEXLib*>(GetXLib())->doStartup();
88cdf0e10cSrcweir     // clean up own members
89cdf0e10cSrcweir     doDestruct();
90cdf0e10cSrcweir     // prevent SalDisplay from closing KApplication's display
91cdf0e10cSrcweir     pDisp_ = NULL;
92cdf0e10cSrcweir }
93cdf0e10cSrcweir 
94cdf0e10cSrcweir /***************************************************************************
95cdf0e10cSrcweir  * class KDEXLib                                                           *
96cdf0e10cSrcweir  ***************************************************************************/
97cdf0e10cSrcweir 
98cdf0e10cSrcweir KDEXLib::~KDEXLib()
99cdf0e10cSrcweir {
100cdf0e10cSrcweir     // #158056# on 64 bit linux using libXRandr.so.2 will crash in
101cdf0e10cSrcweir     // XCloseDisplay when freeing extension data
102cdf0e10cSrcweir     // no known work around, therefor currently leak. Hopefully
103cdf0e10cSrcweir     // this does not make problems since we're shutting down anyway
104cdf0e10cSrcweir     // should we ever get a real kde plugin that uses the KDE event loop
105cdf0e10cSrcweir     // we should use kde's method to signal screen changes similar
106cdf0e10cSrcweir     // to the gtk plugin
107cdf0e10cSrcweir     #if ! defined USE_RANDR || ! (defined LINUX && defined X86_64)
108cdf0e10cSrcweir     // properly deinitialize KApplication
109cdf0e10cSrcweir     delete (VCLKDEApplication*)m_pApplication;
110cdf0e10cSrcweir     #endif
111cdf0e10cSrcweir     // free the faked cmdline arguments no longer needed by KApplication
112cdf0e10cSrcweir     for( int i = 0; i < m_nFakeCmdLineArgs; i++ )
113cdf0e10cSrcweir         free( m_pFreeCmdLineArgs[i] );
114cdf0e10cSrcweir     delete [] m_pFreeCmdLineArgs;
115cdf0e10cSrcweir     delete [] m_pAppCmdLineArgs;
116cdf0e10cSrcweir }
117cdf0e10cSrcweir 
118cdf0e10cSrcweir void KDEXLib::Init()
119cdf0e10cSrcweir {
120cdf0e10cSrcweir 	SalI18N_InputMethod* pInputMethod = new SalI18N_InputMethod;
121cdf0e10cSrcweir 	pInputMethod->SetLocale();
122cdf0e10cSrcweir 	XrmInitialize();
123cdf0e10cSrcweir 
124*288dd0d8SHerbert Dürr 	KAboutData *kAboutData = new KAboutData( "Apache OpenOffice",
125*288dd0d8SHerbert Dürr 			I18N_NOOP( "Apache OpenOffice" ),
126*288dd0d8SHerbert Dürr 			"3.4.0",
127*288dd0d8SHerbert Dürr 			I18N_NOOP( "Apache OpenOffice with KDE Native Widget Support." ),
128*288dd0d8SHerbert Dürr 			KAboutData::License_File,
129*288dd0d8SHerbert Dürr 			"(c) 2003, 2004 Novell, Inc and Apache Software Foundation",
130*288dd0d8SHerbert Dürr 			I18N_NOOP( "Apache OpenOffice is an office suite.\n" ),
131*288dd0d8SHerbert Dürr 			"http://incubator.apache.org/openofficeorg/index.html",
132*288dd0d8SHerbert Dürr 			"ooo-issues@apache.org");
133cdf0e10cSrcweir 	kAboutData->addAuthor( "Jan Holesovsky",
134cdf0e10cSrcweir 			I18N_NOOP( "Original author and maintainer of the KDE NWF." ),
135cdf0e10cSrcweir 			"kendy@artax.karlin.mff.cuni.cz",
136cdf0e10cSrcweir 			"http://artax.karlin.mff.cuni.cz/~kendy" );
137cdf0e10cSrcweir 
138cdf0e10cSrcweir     m_nFakeCmdLineArgs = 1;
139cdf0e10cSrcweir 	sal_uInt16 nIdx;
140cdf0e10cSrcweir 	vos::OExtCommandLine aCommandLine;
141cdf0e10cSrcweir 	int nParams = aCommandLine.getCommandArgCount();
142cdf0e10cSrcweir 	rtl::OString aDisplay;
143cdf0e10cSrcweir 	rtl::OUString aParam, aBin;
144cdf0e10cSrcweir 
145cdf0e10cSrcweir 	for ( nIdx = 0; nIdx < nParams; ++nIdx )
146cdf0e10cSrcweir 	{
147cdf0e10cSrcweir 		aCommandLine.getCommandArg( nIdx, aParam );
148cdf0e10cSrcweir 		if ( !m_pFreeCmdLineArgs && aParam.equalsAscii( "-display" ) && nIdx + 1 < nParams )
149cdf0e10cSrcweir 		{
150cdf0e10cSrcweir 			aCommandLine.getCommandArg( nIdx + 1, aParam );
151cdf0e10cSrcweir 			aDisplay = rtl::OUStringToOString( aParam, osl_getThreadTextEncoding() );
152cdf0e10cSrcweir 
153cdf0e10cSrcweir 			m_nFakeCmdLineArgs = 3;
154cdf0e10cSrcweir 			m_pFreeCmdLineArgs = new char*[ m_nFakeCmdLineArgs ];
155cdf0e10cSrcweir 			m_pFreeCmdLineArgs[ 1 ] = strdup( "-display" );
156cdf0e10cSrcweir 			m_pFreeCmdLineArgs[ 2 ] = strdup( aDisplay.getStr() );
157cdf0e10cSrcweir 		}
158cdf0e10cSrcweir 	}
159cdf0e10cSrcweir 	if ( !m_pFreeCmdLineArgs )
160cdf0e10cSrcweir 		m_pFreeCmdLineArgs = new char*[ m_nFakeCmdLineArgs ];
161cdf0e10cSrcweir 
162cdf0e10cSrcweir     osl_getExecutableFile( &aParam.pData );
163cdf0e10cSrcweir     osl_getSystemPathFromFileURL( aParam.pData, &aBin.pData );
164cdf0e10cSrcweir     rtl::OString aExec = rtl::OUStringToOString( aBin, osl_getThreadTextEncoding() );
165cdf0e10cSrcweir 	m_pFreeCmdLineArgs[0] = strdup( aExec.getStr() );
166cdf0e10cSrcweir 
167cdf0e10cSrcweir     // make a copy of the string list for freeing it since
168cdf0e10cSrcweir     // KApplication manipulates the pointers inside the argument vector
169cdf0e10cSrcweir     // note: KApplication bad !
170cdf0e10cSrcweir     m_pAppCmdLineArgs = new char*[ m_nFakeCmdLineArgs ];
171cdf0e10cSrcweir     for( int i = 0; i < m_nFakeCmdLineArgs; i++ )
172cdf0e10cSrcweir         m_pAppCmdLineArgs[i] = m_pFreeCmdLineArgs[i];
173cdf0e10cSrcweir 
174cdf0e10cSrcweir 	KCmdLineArgs::init( m_nFakeCmdLineArgs, m_pAppCmdLineArgs, kAboutData );
175cdf0e10cSrcweir 
176cdf0e10cSrcweir 	KApplication::disableAutoDcopRegistration();
177cdf0e10cSrcweir 	m_pApplication = new VCLKDEApplication();
178cdf0e10cSrcweir     kapp->disableSessionManagement();
179cdf0e10cSrcweir 
180cdf0e10cSrcweir 	Display* pDisp = QPaintDevice::x11AppDisplay();
181cdf0e10cSrcweir 
182cdf0e10cSrcweir 	SalDisplay *pSalDisplay = new SalKDEDisplay( pDisp );
183cdf0e10cSrcweir 
184cdf0e10cSrcweir 	pInputMethod->CreateMethod( pDisp );
185cdf0e10cSrcweir 	pInputMethod->AddConnectionWatch( pDisp, (void*)this );
186cdf0e10cSrcweir 	pSalDisplay->SetInputMethod( pInputMethod );
187cdf0e10cSrcweir 
188cdf0e10cSrcweir     PushXErrorLevel( true );
189cdf0e10cSrcweir 	SalI18N_KeyboardExtension *pKbdExtension = new SalI18N_KeyboardExtension( pDisp );
190cdf0e10cSrcweir 	XSync( pDisp, False );
191cdf0e10cSrcweir 
192cdf0e10cSrcweir 	pKbdExtension->UseExtension( ! HasXErrorOccured() );
193cdf0e10cSrcweir 	PopXErrorLevel();
194cdf0e10cSrcweir 
195cdf0e10cSrcweir 	pSalDisplay->SetKbdExtension( pKbdExtension );
196cdf0e10cSrcweir }
197cdf0e10cSrcweir 
198cdf0e10cSrcweir void KDEXLib::doStartup()
199cdf0e10cSrcweir {
200cdf0e10cSrcweir     if( ! m_bStartupDone )
201cdf0e10cSrcweir     {
202cdf0e10cSrcweir         KStartupInfo::appStarted();
203cdf0e10cSrcweir         m_bStartupDone = true;
204cdf0e10cSrcweir         #if OSL_DEBUG_LEVEL > 1
205cdf0e10cSrcweir         fprintf( stderr, "called KStartupInfo::appStarted()\n" );
206cdf0e10cSrcweir         #endif
207cdf0e10cSrcweir     }
208cdf0e10cSrcweir }
209cdf0e10cSrcweir 
210cdf0e10cSrcweir /**********************************************************************
211cdf0e10cSrcweir  * class KDEData                                                      *
212cdf0e10cSrcweir  **********************************************************************/
213cdf0e10cSrcweir 
214cdf0e10cSrcweir KDEData::~KDEData()
215cdf0e10cSrcweir {
216cdf0e10cSrcweir }
217cdf0e10cSrcweir 
218cdf0e10cSrcweir void KDEData::Init()
219cdf0e10cSrcweir {
220cdf0e10cSrcweir     pXLib_ = new KDEXLib();
221cdf0e10cSrcweir     pXLib_->Init();
222cdf0e10cSrcweir }
223cdf0e10cSrcweir 
224cdf0e10cSrcweir /**********************************************************************
225cdf0e10cSrcweir  * plugin entry point                                                 *
226cdf0e10cSrcweir  **********************************************************************/
227cdf0e10cSrcweir 
228cdf0e10cSrcweir extern "C" {
229cdf0e10cSrcweir     VCLPLUG_KDE_PUBLIC SalInstance* create_SalInstance( oslModule )
230cdf0e10cSrcweir     {
231cdf0e10cSrcweir         /* #i92121# workaround deadlocks in the X11 implementation
232cdf0e10cSrcweir         */
233cdf0e10cSrcweir         static const char* pNoXInitThreads = getenv( "SAL_NO_XINITTHREADS" );
234cdf0e10cSrcweir         /* #i90094#
235cdf0e10cSrcweir            from now on we know that an X connection will be
236cdf0e10cSrcweir            established, so protect X against itself
237cdf0e10cSrcweir         */
238cdf0e10cSrcweir         if( ! ( pNoXInitThreads && *pNoXInitThreads ) )
239cdf0e10cSrcweir             XInitThreads();
240cdf0e10cSrcweir 
241cdf0e10cSrcweir         rtl::OString aVersion( qVersion() );
242cdf0e10cSrcweir #if OSL_DEBUG_LEVEL > 1
243cdf0e10cSrcweir         fprintf( stderr, "qt version string is \"%s\"\n", aVersion.getStr() );
244cdf0e10cSrcweir #endif
245cdf0e10cSrcweir         sal_Int32 nIndex = 0, nMajor = 0, nMinor = 0, nMicro = 0;
246cdf0e10cSrcweir         nMajor = aVersion.getToken( 0, '.', nIndex ).toInt32();
247cdf0e10cSrcweir         if( nIndex > 0 )
248cdf0e10cSrcweir             nMinor = aVersion.getToken( 0, '.', nIndex ).toInt32();
249cdf0e10cSrcweir         if( nIndex > 0 )
250cdf0e10cSrcweir             nMicro = aVersion.getToken( 0, '.', nIndex ).toInt32();
251cdf0e10cSrcweir         if( nMajor != 3 || nMinor < 2 || (nMinor == 2 && nMicro < 2) )
252cdf0e10cSrcweir         {
253cdf0e10cSrcweir #if OSL_DEBUG_LEVEL > 1
254cdf0e10cSrcweir             fprintf( stderr, "unsuitable qt version %d.%d.%d\n", (int)nMajor, (int)nMinor, (int)nMicro );
255cdf0e10cSrcweir #endif
256cdf0e10cSrcweir             return NULL;
257cdf0e10cSrcweir         }
258cdf0e10cSrcweir 
259cdf0e10cSrcweir         KDESalInstance* pInstance = new KDESalInstance( new SalYieldMutex() );
260cdf0e10cSrcweir #if OSL_DEBUG_LEVEL > 1
261cdf0e10cSrcweir         fprintf( stderr, "created KDESalInstance 0x%p\n", pInstance );
262cdf0e10cSrcweir #endif
263cdf0e10cSrcweir 
264cdf0e10cSrcweir         // initialize SalData
265cdf0e10cSrcweir         KDEData *pSalData = new KDEData();
266cdf0e10cSrcweir         SetSalData( pSalData );
267cdf0e10cSrcweir         pSalData->m_pInstance = pInstance;
268cdf0e10cSrcweir         pSalData->Init();
269cdf0e10cSrcweir         pSalData->initNWF();
270cdf0e10cSrcweir 
271cdf0e10cSrcweir         return pInstance;
272cdf0e10cSrcweir     }
273cdf0e10cSrcweir }
274