khtml Library API Documentation

kjavaappletserver.cpp

00001 /* This file is part of the KDE project 00002 * 00003 * Copyright (C) 2000 Richard Moore <rich@kde.org> 00004 * 2000 Wynn Wilkes <wynnw@caldera.com> 00005 * 00006 * This library is free software; you can redistribute it and/or 00007 * modify it under the terms of the GNU Library General Public 00008 * License as published by the Free Software Foundation; either 00009 * version 2 of the License, or (at your option) any later version. 00010 * 00011 * This library is distributed in the hope that it will be useful, 00012 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00014 * Library General Public License for more details. 00015 * 00016 * You should have received a copy of the GNU Library General Public License 00017 * along with this library; see the file COPYING.LIB. If not, write to 00018 * the Free Software Foundation, Inc., 59 Temple Place - Suite 330, 00019 * Boston, MA 02111-1307, USA. 00020 */ 00021 00022 #include <config.h> 00023 #include "kjavaappletserver.h" 00024 #include "kjavaappletcontext.h" 00025 #include "kjavaprocess.h" 00026 #include "kjavadownloader.h" 00027 00028 #include <kdebug.h> 00029 #include <kconfig.h> 00030 #include <klocale.h> 00031 #include <kparts/browserextension.h> 00032 #include <kapplication.h> 00033 #include <kstandarddirs.h> 00034 00035 #include <kio/job.h> 00036 #include <kio/kprotocolmanager.h> 00037 #include <ksslcertificate.h> 00038 #include <ksslcertchain.h> 00039 #include <kssl.h> 00040 00041 #include <qtimer.h> 00042 #include <qguardedptr.h> 00043 #include <qvaluelist.h> 00044 #include <qptrlist.h> 00045 #include <qdir.h> 00046 #include <qeventloop.h> 00047 #include <qapplication.h> 00048 #include <qlabel.h> 00049 #include <qdialog.h> 00050 #include <qpushbutton.h> 00051 #include <qlayout.h> 00052 #include <qregexp.h> 00053 00054 #include <stdlib.h> 00055 #include <assert.h> 00056 00057 #define KJAS_CREATE_CONTEXT (char)1 00058 #define KJAS_DESTROY_CONTEXT (char)2 00059 #define KJAS_CREATE_APPLET (char)3 00060 #define KJAS_DESTROY_APPLET (char)4 00061 #define KJAS_START_APPLET (char)5 00062 #define KJAS_STOP_APPLET (char)6 00063 #define KJAS_INIT_APPLET (char)7 00064 #define KJAS_SHOW_DOCUMENT (char)8 00065 #define KJAS_SHOW_URLINFRAME (char)9 00066 #define KJAS_SHOW_STATUS (char)10 00067 #define KJAS_RESIZE_APPLET (char)11 00068 #define KJAS_GET_URLDATA (char)12 00069 #define KJAS_URLDATA (char)13 00070 #define KJAS_SHUTDOWN_SERVER (char)14 00071 #define KJAS_JAVASCRIPT_EVENT (char)15 00072 #define KJAS_GET_MEMBER (char)16 00073 #define KJAS_CALL_MEMBER (char)17 00074 #define KJAS_PUT_MEMBER (char)18 00075 #define KJAS_DEREF_OBJECT (char)19 00076 #define KJAS_AUDIOCLIP_PLAY (char)20 00077 #define KJAS_AUDIOCLIP_LOOP (char)21 00078 #define KJAS_AUDIOCLIP_STOP (char)22 00079 #define KJAS_APPLET_STATE (char)23 00080 #define KJAS_APPLET_FAILED (char)24 00081 #define KJAS_DATA_COMMAND (char)25 00082 #define KJAS_PUT_URLDATA (char)26 00083 #define KJAS_PUT_DATA (char)27 00084 #define KJAS_SECURITY_CONFIRM (char)28 00085 00086 00087 class JSStackFrame; 00088 00089 typedef QMap< int, KJavaKIOJob* > KIOJobMap; 00090 typedef QMap< int, JSStackFrame* > JSStack; 00091 00092 class JSStackFrame { 00093 public: 00094 JSStackFrame(JSStack & stack, QStringList & a) 00095 : jsstack(stack), args(a), ticket(counter++), ready(false), exit (false) { 00096 jsstack.insert( ticket, this ); 00097 } 00098 ~JSStackFrame() { 00099 jsstack.erase( ticket ); 00100 } 00101 JSStack & jsstack; 00102 QStringList & args; 00103 int ticket; 00104 bool ready : 1; 00105 bool exit : 1; 00106 static int counter; 00107 }; 00108 00109 int JSStackFrame::counter = 0; 00110 00111 class KJavaAppletServerPrivate 00112 { 00113 friend class KJavaAppletServer; 00114 private: 00115 KJavaAppletServerPrivate() : kssl( 0L ) {} 00116 ~KJavaAppletServerPrivate() { 00117 delete kssl; 00118 } 00119 int counter; 00120 QMap< int, QGuardedPtr<KJavaAppletContext> > contexts; 00121 QString appletLabel; 00122 JSStack jsstack; 00123 KIOJobMap kiojobs; 00124 bool javaProcessFailed; 00125 bool useKIO; 00126 KSSL * kssl; 00127 //int locked_context; 00128 //QValueList<QByteArray> java_requests; 00129 }; 00130 00131 static KJavaAppletServer* self = 0; 00132 00133 KJavaAppletServer::KJavaAppletServer() 00134 { 00135 d = new KJavaAppletServerPrivate; 00136 process = new KJavaProcess(); 00137 00138 connect( process, SIGNAL(received(const QByteArray&)), 00139 this, SLOT(slotJavaRequest(const QByteArray&)) ); 00140 00141 setupJava( process ); 00142 00143 if( process->startJava() ) { 00144 d->appletLabel = i18n( "Loading Applet" ); 00145 d->javaProcessFailed = false; 00146 } 00147 else { 00148 d->appletLabel = i18n( "Error: java executable not found" ); 00149 d->javaProcessFailed = true; 00150 } 00151 } 00152 00153 KJavaAppletServer::~KJavaAppletServer() 00154 { 00155 quit(); 00156 00157 delete process; 00158 delete d; 00159 } 00160 00161 QString KJavaAppletServer::getAppletLabel() 00162 { 00163 if( self ) 00164 return self->appletLabel(); 00165 else 00166 return QString::null; 00167 } 00168 00169 QString KJavaAppletServer::appletLabel() 00170 { 00171 return d->appletLabel; 00172 } 00173 00174 KJavaAppletServer* KJavaAppletServer::allocateJavaServer() 00175 { 00176 if( self == 0 ) 00177 { 00178 self = new KJavaAppletServer(); 00179 self->d->counter = 0; 00180 } 00181 00182 self->d->counter++; 00183 return self; 00184 } 00185 00186 void KJavaAppletServer::freeJavaServer() 00187 { 00188 self->d->counter--; 00189 00190 if( self->d->counter == 0 ) 00191 { 00192 //instead of immediately quitting here, set a timer to kill us 00193 //if there are still no servers- give us one minute 00194 //this is to prevent repeated loading and unloading of the jvm 00195 KConfig config( "konquerorrc", true ); 00196 config.setGroup( "Java/JavaScript Settings" ); 00197 if( config.readBoolEntry( "ShutdownAppletServer", true ) ) 00198 { 00199 int value = config.readNumEntry( "AppletServerTimeout", 60 ); 00200 QTimer::singleShot( value*1000, self, SLOT( checkShutdown() ) ); 00201 } 00202 } 00203 } 00204 00205 void KJavaAppletServer::checkShutdown() 00206 { 00207 if( self->d->counter == 0 ) 00208 { 00209 delete self; 00210 self = 0; 00211 } 00212 } 00213 00214 void KJavaAppletServer::setupJava( KJavaProcess *p ) 00215 { 00216 KConfig config ( "konquerorrc", true ); 00217 config.setGroup( "Java/JavaScript Settings" ); 00218 00219 QString jvm_path = "java"; 00220 00221 QString jPath = config.readPathEntry( "JavaPath" ); 00222 if ( !jPath.isEmpty() && jPath != "java" ) 00223 { 00224 // Cut off trailing slash if any 00225 if( jPath[jPath.length()-1] == '/' ) 00226 jPath.remove(jPath.length()-1, 1); 00227 00228 QDir dir( jPath ); 00229 if( dir.exists( "bin/java" ) ) 00230 { 00231 jvm_path = jPath + "/bin/java"; 00232 } 00233 else if (dir.exists( "/jre/bin/java" ) ) 00234 { 00235 jvm_path = jPath + "/jre/bin/java"; 00236 } 00237 else if( QFile::exists(jPath) ) 00238 { 00239 //check here to see if they entered the whole path the java exe 00240 jvm_path = jPath; 00241 } 00242 } 00243 00244 //check to see if jvm_path is valid and set d->appletLabel accordingly 00245 p->setJVMPath( jvm_path ); 00246 00247 // Prepare classpath variable 00248 QString kjava_class = locate("data", "kjava/kjava.jar"); 00249 kdDebug(6100) << "kjava_class = " << kjava_class << endl; 00250 if( kjava_class.isNull() ) // Should not happen 00251 return; 00252 00253 QDir dir( kjava_class ); 00254 dir.cdUp(); 00255 kdDebug(6100) << "dir = " << dir.absPath() << endl; 00256 00257 QStringList entries = dir.entryList( "*.jar" ); 00258 kdDebug(6100) << "entries = " << entries.join( ":" ) << endl; 00259 00260 QString classes; 00261 for( QStringList::Iterator it = entries.begin(); 00262 it != entries.end(); it++ ) 00263 { 00264 if( !classes.isEmpty() ) 00265 classes += ":"; 00266 classes += dir.absFilePath( *it ); 00267 } 00268 p->setClasspath( classes ); 00269 00270 // Fix all the extra arguments 00271 QString extraArgs = config.readEntry( "JavaArgs" ); 00272 p->setExtraArgs( extraArgs ); 00273 00274 if( config.readBoolEntry( "ShowJavaConsole", false) ) 00275 { 00276 p->setSystemProperty( "kjas.showConsole", QString::null ); 00277 } 00278 00279 if( config.readBoolEntry( "UseSecurityManager", true ) ) 00280 { 00281 QString class_file = locate( "data", "kjava/kjava.policy" ); 00282 p->setSystemProperty( "java.security.policy", class_file ); 00283 00284 p->setSystemProperty( "java.security.manager", 00285 "org.kde.kjas.server.KJASSecurityManager" ); 00286 } 00287 00288 d->useKIO = config.readBoolEntry( "UseKio", false); 00289 if( d->useKIO ) 00290 { 00291 p->setSystemProperty( "kjas.useKio", QString::null ); 00292 } 00293 00294 //check for http proxies... 00295 if( KProtocolManager::useProxy() ) 00296 { 00297 // only proxyForURL honors automatic proxy scripts 00298 // we do not know the applet url here so we just use a dummy url 00299 // this is a workaround for now 00300 // FIXME 00301 KURL dummyURL( "http://www.kde.org/" ); 00302 QString httpProxy = KProtocolManager::proxyForURL(dummyURL); 00303 kdDebug(6100) << "httpProxy is " << httpProxy << endl; 00304 00305 KURL url( httpProxy ); 00306 p->setSystemProperty( "http.proxyHost", url.host() ); 00307 p->setSystemProperty( "http.proxyPort", QString::number( url.port() ) ); 00308 } 00309 00310 //set the main class to run 00311 p->setMainClass( "org.kde.kjas.server.Main" ); 00312 } 00313 00314 void KJavaAppletServer::createContext( int contextId, KJavaAppletContext* context ) 00315 { 00316 // kdDebug(6100) << "createContext: " << contextId << endl; 00317 if ( d->javaProcessFailed ) return; 00318 00319 d->contexts.insert( contextId, context ); 00320 00321 QStringList args; 00322 args.append( QString::number( contextId ) ); 00323 process->send( KJAS_CREATE_CONTEXT, args ); 00324 } 00325 00326 void KJavaAppletServer::destroyContext( int contextId ) 00327 { 00328 // kdDebug(6100) << "destroyContext: " << contextId << endl; 00329 if ( d->javaProcessFailed ) return; 00330 d->contexts.remove( contextId ); 00331 00332 QStringList args; 00333 args.append( QString::number( contextId ) ); 00334 process->send( KJAS_DESTROY_CONTEXT, args ); 00335 } 00336 00337 bool KJavaAppletServer::createApplet( int contextId, int appletId, 00338 const QString & name, const QString & clazzName, 00339 const QString & baseURL, const QString & user, 00340 const QString & password, const QString & authname, 00341 const QString & codeBase, const QString & jarFile, 00342 QSize size, const QMap<QString,QString>& params, 00343 const QString & windowTitle ) 00344 { 00345 // kdDebug(6100) << "createApplet: contextId = " << contextId << endl 00346 // << " appletId = " << appletId << endl 00347 // << " name = " << name << endl 00348 // << " clazzName = " << clazzName << endl 00349 // << " baseURL = " << baseURL << endl 00350 // << " codeBase = " << codeBase << endl 00351 // << " jarFile = " << jarFile << endl 00352 // << " width = " << size.width() << endl 00353 // << " height = " << size.height() << endl; 00354 00355 if ( d->javaProcessFailed ) return false; 00356 00357 QStringList args; 00358 args.append( QString::number( contextId ) ); 00359 args.append( QString::number( appletId ) ); 00360 00361 //it's ok if these are empty strings, I take care of it later... 00362 args.append( name ); 00363 args.append( clazzName ); 00364 args.append( baseURL ); 00365 args.append( user ); 00366 args.append( password ); 00367 args.append( authname ); 00368 args.append( codeBase ); 00369 args.append( jarFile ); 00370 00371 args.append( QString::number( size.width() ) ); 00372 args.append( QString::number( size.height() ) ); 00373 00374 args.append( windowTitle ); 00375 00376 //add on the number of parameter pairs... 00377 int num = params.count(); 00378 QString num_params = QString("%1").arg( num, 8 ); 00379 args.append( num_params ); 00380 00381 QMap< QString, QString >::ConstIterator it; 00382 00383 for( it = params.begin(); it != params.end(); ++it ) 00384 { 00385 args.append( it.key() ); 00386 args.append( it.data() ); 00387 } 00388 00389 process->send( KJAS_CREATE_APPLET, args ); 00390 00391 return true; 00392 } 00393 00394 void KJavaAppletServer::initApplet( int contextId, int appletId ) 00395 { 00396 if ( d->javaProcessFailed ) return; 00397 QStringList args; 00398 args.append( QString::number( contextId ) ); 00399 args.append( QString::number( appletId ) ); 00400 00401 process->send( KJAS_INIT_APPLET, args ); 00402 } 00403 00404 void KJavaAppletServer::destroyApplet( int contextId, int appletId ) 00405 { 00406 if ( d->javaProcessFailed ) return; 00407 QStringList args; 00408 args.append( QString::number(contextId) ); 00409 args.append( QString::number(appletId) ); 00410 00411 process->send( KJAS_DESTROY_APPLET, args ); 00412 } 00413 00414 void KJavaAppletServer::startApplet( int contextId, int appletId ) 00415 { 00416 if ( d->javaProcessFailed ) return; 00417 QStringList args; 00418 args.append( QString::number(contextId) ); 00419 args.append( QString::number(appletId) ); 00420 00421 process->send( KJAS_START_APPLET, args ); 00422 } 00423 00424 void KJavaAppletServer::stopApplet( int contextId, int appletId ) 00425 { 00426 if ( d->javaProcessFailed ) return; 00427 QStringList args; 00428 args.append( QString::number(contextId) ); 00429 args.append( QString::number(appletId) ); 00430 00431 process->send( KJAS_STOP_APPLET, args ); 00432 } 00433 00434 void KJavaAppletServer::sendURLData( int loaderID, int code, const QByteArray& data ) 00435 { 00436 QStringList args; 00437 args.append( QString::number(loaderID) ); 00438 args.append( QString::number(code) ); 00439 00440 process->send( KJAS_URLDATA, args, data ); 00441 } 00442 00443 void KJavaAppletServer::removeDataJob( int loaderID ) 00444 { 00445 KIOJobMap::iterator it = d->kiojobs.find( loaderID ); 00446 if (it != d->kiojobs.end()) { 00447 it.data()->deleteLater(); 00448 d->kiojobs.erase( it ); 00449 } 00450 } 00451 00452 void KJavaAppletServer::quit() 00453 { 00454 QStringList args; 00455 00456 process->send( KJAS_SHUTDOWN_SERVER, args ); 00457 process->flushBuffers(); 00458 process->wait( 10 ); 00459 } 00460 00461 void KJavaAppletServer::slotJavaRequest( const QByteArray& qb ) 00462 { 00463 // qb should be one command only without the length string, 00464 // we parse out the command and it's meaning here... 00465 QString cmd; 00466 QStringList args; 00467 int index = 0; 00468 int qb_size = qb.size(); 00469 00470 //get the command code 00471 char cmd_code = qb[ index++ ]; 00472 ++index; //skip the next sep 00473 00474 //get contextID 00475 QString contextID; 00476 while( qb[index] != 0 && index < qb_size ) 00477 { 00478 contextID += qb[ index++ ]; 00479 } 00480 bool ok; 00481 int ID_num = contextID.toInt( &ok ); // context id or kio job id 00482 /*if (d->locked_context > -1 && 00483 ID_num != d->locked_context && 00484 (cmd_code == KJAS_JAVASCRIPT_EVENT || 00485 cmd_code == KJAS_APPLET_STATE || 00486 cmd_code == KJAS_APPLET_FAILED)) 00487 { 00488 / * Don't allow requests from other contexts if we're waiting 00489 * on a return value that can trigger JavaScript events 00490 * / 00491 d->java_requests.push_back(qb); 00492 return; 00493 }*/ 00494 ++index; //skip the sep 00495 00496 if (cmd_code == KJAS_PUT_DATA) { 00497 // rest of the data is for kio put 00498 if (ok) { 00499 KIOJobMap::iterator it = d->kiojobs.find( ID_num ); 00500 if (ok && it != d->kiojobs.end()) { 00501 QByteArray qba; 00502 qba.setRawData(qb.data() + index, qb.size() - index - 1); 00503 it.data()->data(qba); 00504 qba.resetRawData(qb.data() + index, qb.size() - index - 1); 00505 } 00506 kdDebug(6100) << "PutData(" << ID_num << ") size=" << qb.size() - index << endl; 00507 } else 00508 kdError(6100) << "PutData error " << ok << endl; 00509 return; 00510 } 00511 //now parse out the arguments 00512 while( index < qb_size ) 00513 { 00514 int sep_pos = qb.find( 0, index ); 00515 if (sep_pos < 0) { 00516 kdError(6100) << "Missing separation byte" << endl; 00517 sep_pos = qb_size; 00518 } 00519 //kdDebug(6100) << "KJavaAppletServer::slotJavaRequest: "<< QString::fromLocal8Bit( qb.data() + index, sep_pos - index ) << endl; 00520 args.append( QString::fromLocal8Bit( qb.data() + index, sep_pos - index ) ); 00521 index = sep_pos + 1; //skip the sep 00522 } 00523 //here I should find the context and call the method directly 00524 //instead of emitting signals 00525 switch( cmd_code ) 00526 { 00527 case KJAS_SHOW_DOCUMENT: 00528 cmd = QString::fromLatin1( "showdocument" ); 00529 break; 00530 00531 case KJAS_SHOW_URLINFRAME: 00532 cmd = QString::fromLatin1( "showurlinframe" ); 00533 break; 00534 00535 case KJAS_SHOW_STATUS: 00536 cmd = QString::fromLatin1( "showstatus" ); 00537 break; 00538 00539 case KJAS_RESIZE_APPLET: 00540 cmd = QString::fromLatin1( "resizeapplet" ); 00541 break; 00542 00543 case KJAS_GET_URLDATA: 00544 if (ok && args.size () > 0) { 00545 d->kiojobs.insert(ID_num, new KJavaDownloader(ID_num, args[0])); 00546 kdDebug(6100) << "GetURLData(" << ID_num << ") url=" << args[0] << endl; 00547 } else 00548 kdError(6100) << "GetURLData error " << ok << " args:" << args.size() << endl; 00549 return; 00550 case KJAS_PUT_URLDATA: 00551 if (ok && args.size () > 0) { 00552 KJavaUploader *job = new KJavaUploader(ID_num, args[0]); 00553 d->kiojobs.insert(ID_num, job); 00554 job->start(); 00555 kdDebug(6100) << "PutURLData(" << ID_num << ") url=" << args[0] << endl; 00556 } else 00557 kdError(6100) << "PutURLData error " << ok << " args:" << args.size() << endl; 00558 return; 00559 case KJAS_DATA_COMMAND: 00560 if (ok && args.size () > 0) { 00561 int cmd = args[0].toInt( &ok ); 00562 KIOJobMap::iterator it = d->kiojobs.find( ID_num ); 00563 if (ok && it != d->kiojobs.end()) 00564 it.data()->jobCommand( cmd ); 00565 kdDebug(6100) << "KIO Data command: " << ID_num << " " << args[0] << endl; 00566 } else 00567 kdError(6100) << "KIO Data command error " << ok << " args:" << args.size() << endl; 00568 return; 00569 case KJAS_JAVASCRIPT_EVENT: 00570 cmd = QString::fromLatin1( "JS_Event" ); 00571 kdDebug(6100) << "Javascript request: "<< contextID 00572 << " code: " << args[0] << endl; 00573 break; 00574 case KJAS_GET_MEMBER: 00575 case KJAS_PUT_MEMBER: 00576 case KJAS_CALL_MEMBER: { 00577 int ticket = args[0].toInt(); 00578 JSStack::iterator it = d->jsstack.find(ticket); 00579 if (it != d->jsstack.end()) { 00580 kdDebug(6100) << "slotJavaRequest: " << ticket << endl; 00581 args.pop_front(); 00582 it.data()->args.operator=(args); // just in case .. 00583 it.data()->ready = true; 00584 it.data()->exit = true; 00585 } else 00586 kdDebug(6100) << "Error: Missed return member data" << endl; 00587 return; 00588 } 00589 case KJAS_AUDIOCLIP_PLAY: 00590 cmd = QString::fromLatin1( "audioclip_play" ); 00591 kdDebug(6100) << "Audio Play: url=" << args[0] << endl; 00592 break; 00593 case KJAS_AUDIOCLIP_LOOP: 00594 cmd = QString::fromLatin1( "audioclip_loop" ); 00595 kdDebug(6100) << "Audio Loop: url=" << args[0] << endl; 00596 break; 00597 case KJAS_AUDIOCLIP_STOP: 00598 cmd = QString::fromLatin1( "audioclip_stop" ); 00599 kdDebug(6100) << "Audio Stop: url=" << args[0] << endl; 00600 break; 00601 case KJAS_APPLET_STATE: 00602 kdDebug(6100) << "Applet State Notification for Applet " << args[0] << ". New state=" << args[1] << endl; 00603 cmd = QString::fromLatin1( "AppletStateNotification" ); 00604 break; 00605 case KJAS_APPLET_FAILED: 00606 kdDebug(6100) << "Applet " << args[0] << " Failed: " << args[1] << endl; 00607 cmd = QString::fromLatin1( "AppletFailed" ); 00608 break; 00609 case KJAS_SECURITY_CONFIRM: { 00610 if (KSSL::doesSSLWork() && !d->kssl) 00611 d->kssl = new KSSL; 00612 QStringList sl; 00613 QCString answer( "invalid" ); 00614 00615 if (!d->kssl) { 00616 answer = "nossl"; 00617 } else if (args.size() > 2) { 00618 int certsnr = args[1].toInt(); 00619 QString text; 00620 QPtrList<KSSLCertificate> certs; 00621 certs.setAutoDelete( true ); 00622 for (int i = certsnr; i >= 0; i--) { 00623 KSSLCertificate * cert = KSSLCertificate::fromString(args[i+2].ascii()); 00624 if (cert) { 00625 certs.prepend(cert); 00626 if (cert->isSigner()) 00627 text += i18n("Signed by (validation: "); 00628 else 00629 text += i18n("Certificate (validation: "); 00630 switch (cert->validate()) { 00631 case KSSLCertificate::Ok: 00632 text += i18n("Ok"); break; 00633 case KSSLCertificate::NoCARoot: 00634 text += i18n("NoCARoot"); break; 00635 case KSSLCertificate::InvalidPurpose: 00636 text += i18n("InvalidPurpose"); break; 00637 case KSSLCertificate::PathLengthExceeded: 00638 text += i18n("PathLengthExceeded"); break; 00639 case KSSLCertificate::InvalidCA: 00640 text += i18n("InvalidCA"); break; 00641 case KSSLCertificate::Expired: 00642 text += i18n("Expired"); break; 00643 case KSSLCertificate::SelfSigned: 00644 text += i18n("SelfSigned"); break; 00645 case KSSLCertificate::ErrorReadingRoot: 00646 text += i18n("ErrorReadingRoot"); break; 00647 case KSSLCertificate::Revoked: 00648 text += i18n("Revoked"); break; 00649 case KSSLCertificate::Untrusted: 00650 text += i18n("Untrusted"); break; 00651 case KSSLCertificate::SignatureFailed: 00652 text += i18n("SignatureFailed"); break; 00653 case KSSLCertificate::Rejected: 00654 text += i18n("Rejected"); break; 00655 case KSSLCertificate::PrivateKeyFailed: 00656 text += i18n("PrivateKeyFailed"); break; 00657 case KSSLCertificate::InvalidHost: 00658 text += i18n("InvalidHost"); break; 00659 case KSSLCertificate::Unknown: 00660 default: 00661 text += i18n("Unknown"); break; 00662 } 00663 text += QString(")\n"); 00664 QString subject = cert->getSubject() + QChar('\n'); 00665 QRegExp reg(QString("/[A-Z]+=")); 00666 int pos = 0; 00667 while ((pos = subject.find(reg, pos)) > -1) 00668 subject.replace(pos, 1, QString("\n ")); 00669 text += subject.mid(1); 00670 } 00671 } 00672 kdDebug(6100) << "Security confirm " << args[0] << certs.count() << endl; 00673 if ( certs.count() ) { 00674 KSSLCertChain chain; 00675 chain.setChain( certs ); 00676 if ( chain.isValid() ) 00677 answer = PermissionDialog( qApp->activeWindow() ).exec( text, args[0] ); 00678 } 00679 } 00680 sl.push_front( QString(answer) ); 00681 sl.push_front( QString::number(ID_num) ); 00682 process->send( KJAS_SECURITY_CONFIRM, sl ); 00683 return; 00684 } 00685 default: 00686 return; 00687 break; 00688 } 00689 00690 00691 if( !ok ) 00692 { 00693 kdError(6100) << "could not parse out contextID to call command on" << endl; 00694 return; 00695 } 00696 00697 KJavaAppletContext* context = d->contexts[ ID_num ]; 00698 if( context ) 00699 context->processCmd( cmd, args ); 00700 else if (cmd != "AppletStateNotification") 00701 kdError(6100) << "no context object for this id" << endl; 00702 } 00703 00704 void KJavaAppletServer::endWaitForReturnData() { 00705 kdDebug(6100) << "KJavaAppletServer::endWaitForReturnData" << endl; 00706 killTimers(); 00707 JSStack::iterator it = d->jsstack.begin(); 00708 for (; it != d->jsstack.end(); ++it) 00709 it.data()->exit = true; 00710 } 00711 00712 void KJavaAppletServer::timerEvent(QTimerEvent *) { 00713 endWaitForReturnData(); 00714 kdDebug(6100) << "KJavaAppletServer::timerEvent timeout" << endl; 00715 } 00716 00717 void KJavaAppletServer::waitForReturnData(JSStackFrame * frame) { 00718 kdDebug(6100) << ">KJavaAppletServer::waitForReturnData" << endl; 00719 killTimers(); 00720 startTimer(15000); 00721 while (!frame->exit) 00722 kapp->eventLoop()->processEvents (QEventLoop::AllEvents | QEventLoop::WaitForMore); 00723 if (d->jsstack.size() <= 1) 00724 killTimers(); 00725 kdDebug(6100) << "<KJavaAppletServer::waitForReturnData stacksize:" << d->jsstack.size() << endl; 00726 } 00727 00728 bool KJavaAppletServer::getMember(QStringList & args, QStringList & ret_args) { 00729 JSStackFrame frame( d->jsstack, ret_args ); 00730 args.push_front( QString::number(frame.ticket) ); 00731 00732 process->send( KJAS_GET_MEMBER, args ); 00733 waitForReturnData( &frame ); 00734 00735 return frame.ready; 00736 } 00737 00738 bool KJavaAppletServer::putMember( QStringList & args ) { 00739 QStringList ret_args; 00740 JSStackFrame frame( d->jsstack, ret_args ); 00741 args.push_front( QString::number(frame.ticket) ); 00742 00743 process->send( KJAS_PUT_MEMBER, args ); 00744 waitForReturnData( &frame ); 00745 00746 return frame.ready && ret_args.count() > 0 && ret_args[0].toInt(); 00747 } 00748 00749 bool KJavaAppletServer::callMember(QStringList & args, QStringList & ret_args) { 00750 JSStackFrame frame( d->jsstack, ret_args ); 00751 args.push_front( QString::number(frame.ticket) ); 00752 00753 process->send( KJAS_CALL_MEMBER, args ); 00754 waitForReturnData( &frame ); 00755 00756 return frame.ready; 00757 } 00758 00759 void KJavaAppletServer::derefObject( QStringList & args ) { 00760 process->send( KJAS_DEREF_OBJECT, args ); 00761 } 00762 00763 bool KJavaAppletServer::usingKIO() { 00764 return d->useKIO; 00765 } 00766 00767 00768 PermissionDialog::PermissionDialog( QWidget* parent ) 00769 : QObject(parent), m_button("no") 00770 {} 00771 00772 QCString PermissionDialog::exec( const QString & cert, const QString & perm ) { 00773 QGuardedPtr<QDialog> dialog = new QDialog( static_cast<QWidget*>(parent()), "PermissionDialog"); 00774 00775 dialog->setSizePolicy( QSizePolicy( (QSizePolicy::SizeType)1, (QSizePolicy::SizeType)1, 0, 0, dialog->sizePolicy().hasHeightForWidth() ) ); 00776 dialog->setModal( true ); 00777 dialog->setCaption( i18n("Security Alert") ); 00778 00779 QVBoxLayout * dialogLayout = new QVBoxLayout( dialog, 11, 6, "dialogLayout"); 00780 00781 dialogLayout->addWidget( new QLabel( i18n("Do you grant Java applet with certificate(s):"), dialog ) ); 00782 dialogLayout->addWidget( new QLabel( cert, dialog, "message" ) ); 00783 dialogLayout->addWidget( new QLabel( i18n("the following permission"), dialog, "message" ) ); 00784 dialogLayout->addWidget( new QLabel( perm, dialog, "message" ) ); 00785 QSpacerItem * spacer2 = new QSpacerItem( 20, 40, QSizePolicy::Minimum, QSizePolicy::Expanding ); 00786 dialogLayout->addItem( spacer2 ); 00787 00788 QHBoxLayout * buttonLayout = new QHBoxLayout( 0, 0, 6, "buttonLayout"); 00789 00790 QPushButton * no = new QPushButton( i18n("&No"), dialog, "no" ); 00791 no->setDefault( true ); 00792 buttonLayout->addWidget( no ); 00793 00794 QPushButton * reject = new QPushButton( i18n("&Reject All"), dialog, "reject" ); 00795 buttonLayout->addWidget( reject ); 00796 00797 QPushButton * yes = new QPushButton( i18n("&Yes"), dialog, "yes" ); 00798 buttonLayout->addWidget( yes ); 00799 00800 QPushButton * grant = new QPushButton( i18n("&Grant All"), dialog, "grant" ); 00801 buttonLayout->addWidget( grant ); 00802 dialogLayout->addLayout( buttonLayout ); 00803 dialog->resize( dialog->minimumSizeHint() ); 00804 //clearWState( WState_Polished ); 00805 00806 connect( no, SIGNAL( clicked() ), this, SLOT( clicked() ) ); 00807 connect( reject, SIGNAL( clicked() ), this, SLOT( clicked() ) ); 00808 connect( yes, SIGNAL( clicked() ), this, SLOT( clicked() ) ); 00809 connect( grant, SIGNAL( clicked() ), this, SLOT( clicked() ) ); 00810 00811 dialog->exec(); 00812 delete dialog; 00813 00814 return m_button; 00815 } 00816 00817 PermissionDialog::~PermissionDialog() 00818 {} 00819 00820 void PermissionDialog::clicked() 00821 { 00822 m_button = sender()->name(); 00823 static_cast<const QWidget*>(sender())->parentWidget()->close(); 00824 } 00825 00826 #include "kjavaappletserver.moc"
KDE Logo
This file is part of the documentation for khtml Library Version 3.3.0.
Documentation copyright © 1996-2004 the KDE developers.
Generated on Wed Sep 29 09:42:28 2004 by doxygen 1.3.8 written by Dimitri van Heesch, © 1997-2003