summaryrefslogtreecommitdiff
Side-by-side diff
Diffstat (more/less context) (ignore whitespace changes)
-rw-r--r--core/launcher/desktop.cpp4
-rw-r--r--core/launcher/launcher.pro2
-rw-r--r--core/launcher/qcopbridge.cpp424
-rw-r--r--core/launcher/qcopbridge.h7
-rw-r--r--core/launcher/transferserver.cpp213
-rw-r--r--core/launcher/transferserver.h23
6 files changed, 392 insertions, 281 deletions
diff --git a/core/launcher/desktop.cpp b/core/launcher/desktop.cpp
index 24dce73..541b4be 100644
--- a/core/launcher/desktop.cpp
+++ b/core/launcher/desktop.cpp
@@ -561,18 +561,18 @@ void Desktop::execAutoStart() {
cfg.setGroup( "AutoStart" );
appName = cfg.readEntry("Apps", "");
delay = (cfg.readEntry("Delay", "0" )).toInt();
// If the time between suspend and resume was longer then the
// value saved as delay, start the app
if ( suspendTime.secsTo(now) >= (delay*60) ) {
QCopEnvelope e("QPE/System", "execute(QString)");
e << QString(appName);
- } else {
- }
+ } //else {
+ //}
}
#if defined(QPE_HAVE_TOGGLELIGHT)
#include <qpe/config.h>
#include <sys/ioctl.h>
#include <sys/types.h>
#include <fcntl.h>
diff --git a/core/launcher/launcher.pro b/core/launcher/launcher.pro
index ccf8231..169edc1 100644
--- a/core/launcher/launcher.pro
+++ b/core/launcher/launcher.pro
@@ -94,17 +94,17 @@ SOURCES = background.cpp \
INTERFACES = syncdialog.ui
INCLUDEPATH += $(OPIEDIR)/include
DEPENDPATH += $(OPIEDIR)/include .
INCLUDEPATH += $(OPIEDIR)/core/apps/calibrate
DEPENDPATH += $(OPIEDIR)/core/apps/calibrate
INCLUDEPATH += $(OPIEDIR)/rsync
DEPENDPATH += $(OPIEDIR)/rsync
TARGET = qpe
-LIBS += -lqpe -lcrypt -lopie
+LIBS += -lqpe -lcrypt -lopie -luuid
TRANSLATIONS = ../../i18n/de/qpe.ts \
../../i18n/en/qpe.ts \
../../i18n/es/qpe.ts \
../../i18n/fr/qpe.ts \
../../i18n/hu/qpe.ts \
../../i18n/ja/qpe.ts \
../../i18n/ko/qpe.ts \
diff --git a/core/launcher/qcopbridge.cpp b/core/launcher/qcopbridge.cpp
index 2d084fc..85993ee 100644
--- a/core/launcher/qcopbridge.cpp
+++ b/core/launcher/qcopbridge.cpp
@@ -1,12 +1,12 @@
/**********************************************************************
-** Copyright (C) 2000 Trolltech AS. All rights reserved.
+** Copyright (C) 2000-2002 Trolltech AS. All rights reserved.
**
-** This file is part of Qtopia Environment.
+** This file is part of the Qtopia Environment.
**
** This file may be distributed and/or modified under the terms of the
** GNU General Public License version 2 as published by the Free Software
** Foundation and appearing in the file LICENSE.GPL included in the
** packaging of this file.
**
** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
@@ -16,194 +16,226 @@
** Contact info@trolltech.com if any conditions of this licensing are
** not clear to you.
**
**********************************************************************/
#include "qcopbridge.h"
#include "transferserver.h"
+#ifdef QWS
#include <qpe/qcopenvelope_qws.h>
+#endif
#include <qpe/qpeapplication.h>
+#include <qpe/version.h>
#include <qdir.h>
#include <qfile.h>
#include <qtextstream.h>
#include <qdatastream.h>
#include <qstringlist.h>
#include <qfileinfo.h>
#include <qregexp.h>
+#ifdef QWS
#include <qcopchannel_qws.h>
+#endif
-// actually this is wrong, _XOPEN_SOURCE should get defined on the commandline
-// and it should have a proper value assigned. (Simon)
-#if !defined(_XOPEN_SOURCE)
#define _XOPEN_SOURCE
-#endif
#include <pwd.h>
#include <sys/types.h>
#include <unistd.h>
#if defined(_OS_LINUX_)
#include <shadow.h>
#endif
//#define INSECURE
const int block_size = 51200;
-QCopBridge::QCopBridge( Q_UINT16 port, QObject *parent,
+QCopBridge::QCopBridge( Q_UINT16 port, QObject *parent ,
const char* name )
: QServerSocket( port, 1, parent, name ),
desktopChannel( 0 ),
cardChannel( 0 )
{
if ( !ok() )
- qWarning( "Failed to bind to port %d", port );
+ qWarning( "Failed to bind to port %d", port );
else {
- desktopChannel = new QCopChannel( "QPE/Desktop", this );
- connect( desktopChannel, SIGNAL(received(const QCString &, const QByteArray &)),
- this, SLOT(desktopMessage( const QCString &, const QByteArray &)) );
- cardChannel = new QCopChannel( "QPE/Card", this );
- connect( cardChannel, SIGNAL(received(const QCString &, const QByteArray &)),
- this, SLOT(desktopMessage( const QCString &, const QByteArray &)) );
+#ifndef QT_NO_COP
+ desktopChannel = new QCopChannel( "QPE/Desktop", this );
+ connect( desktopChannel, SIGNAL(received(const QCString &, const QByteArray &)),
+ this, SLOT(desktopMessage( const QCString &, const QByteArray &)) );
+ cardChannel = new QCopChannel( "QPE/Card", this );
+ connect( cardChannel, SIGNAL(received(const QCString &, const QByteArray &)),
+ this, SLOT(desktopMessage( const QCString &, const QByteArray &)) );
+#endif
}
sendSync = FALSE;
}
QCopBridge::~QCopBridge()
{
+#ifndef QT_NO_COP
delete desktopChannel;
+#endif
}
void QCopBridge::newConnection( int socket )
{
QCopBridgePI *pi = new QCopBridgePI( socket, this );
openConnections.append( pi );
connect ( pi, SIGNAL( connectionClosed( QCopBridgePI *) ), this, SLOT( connectionClosed( QCopBridgePI *) ) );
+#ifndef QT_NO_COP
QCopEnvelope( "QPE/System", "setScreenSaverMode(int)" ) << QPEApplication::DisableSuspend;
-
+#endif
+
if ( sendSync ) {
- pi ->startSync();
- sendSync = FALSE;
+ pi ->startSync();
+ sendSync = FALSE;
}
}
void QCopBridge::connectionClosed( QCopBridgePI *pi )
{
openConnections.remove( pi );
if ( openConnections.count() == 0 ) {
- QCopEnvelope( "QPE/System", "setScreenSaverMode(int)" ) << QPEApplication::Enable;
+#ifndef QT_NO_COP
+ QCopEnvelope( "QPE/System", "setScreenSaverMode(int)" ) << QPEApplication::Enable;
+#endif
}
-}
+}
void QCopBridge::closeOpenConnections()
{
QCopBridgePI *pi;
for ( pi = openConnections.first(); pi != 0; pi = openConnections.next() )
- pi->close();
+ pi->close();
}
void QCopBridge::desktopMessage( const QCString &command, const QByteArray &args )
{
command.stripWhiteSpace();
int paren = command.find( "(" );
if ( paren <= 0 ) {
- qDebug("DesktopMessage: bad qcop syntax");
- return;
+ qDebug("DesktopMessage: bad qcop syntax");
+ return;
}
QString params = command.mid( paren + 1 );
if ( params[params.length()-1] != ')' ) {
- qDebug("DesktopMessage: bad qcop syntax");
- return;
+ qDebug("DesktopMessage: bad qcop syntax");
+ return;
}
params.truncate( params.length()-1 );
QStringList paramList = QStringList::split( ",", params );
QString data;
if ( paramList.count() ) {
- QDataStream stream( args, IO_ReadOnly );
- for ( QStringList::Iterator it = paramList.begin(); it != paramList.end(); ++it ) {
- QString str;
- if ( *it == "QString" ) {
- stream >> str;
- } else if ( *it == "QCString" ) {
- QCString cstr;
- stream >> cstr;
- str = QString::fromLocal8Bit( cstr );
- } else if ( *it == "int" ) {
- int i;
- stream >> i;
- str = QString::number( i );
- } else if ( *it == "bool" ) {
- int i;
- stream >> i;
- str = QString::number( i );
- } else {
- qDebug(" cannot route the argument type %s through the qcop bridge", (*it).latin1() );
- return;
- }
- str.replace( QRegExp("&"), "&amp;" );
- str.replace( QRegExp(" "), "&0x20;" );
- str.replace( QRegExp("\n"), "&0x0d;" );
- str.replace( QRegExp("\r"), "&0x0a;" );
- data += " " + str;
- }
+ QDataStream stream( args, IO_ReadOnly );
+ for ( QStringList::Iterator it = paramList.begin(); it != paramList.end(); ++it ) {
+ QString str;
+ if ( *it == "QString" ) {
+ stream >> str;
+ } else if ( *it == "QCString" ) {
+ QCString cstr;
+ stream >> cstr;
+ str = QString::fromLocal8Bit( cstr );
+ } else if ( *it == "int" ) {
+ int i;
+ stream >> i;
+ str = QString::number( i );
+ } else if ( *it == "bool" ) {
+ int i;
+ stream >> i;
+ str = QString::number( i );
+ } else {
+ qDebug(" cannot route the argument type %s throught the qcop bridge", (*it).latin1() );
+ return;
+ }
+ QString estr;
+ for (int i=0; i<(int)str.length(); i++) {
+ QChar ch = str[i];
+ if ( ch.row() )
+ goto quick;
+ switch (ch.cell()) {
+ case '&':
+ estr.append( "&amp;" );
+ break;
+ case ' ':
+ estr.append( "&0x20;" );
+ break;
+ case '\n':
+ estr.append( "&0x0d;" );
+ break;
+ case '\r':
+ estr.append( "&0x0a;" );
+ break;
+ default: quick:
+ estr.append(ch);
+ }
+ }
+ data += " " + estr;
+ }
}
QString sendCommand = QString(command.data()) + data;
// send the command to all open connections
if ( command == "startSync()" ) {
- // we need to buffer it a bit
- sendSync = TRUE;
- startTimer( 20000 );
- }
-
+ // we need to buffer it a bit
+ sendSync = TRUE;
+ startTimer( 20000 );
+ }
+
QCopBridgePI *pi;
for ( pi = openConnections.first(); pi != 0; pi = openConnections.next() ) {
- pi->sendDesktopMessage( sendCommand );
+ pi->sendDesktopMessage( sendCommand );
}
}
void QCopBridge::timerEvent( QTimerEvent * )
{
sendSync = FALSE;
killTimers();
}
-QCopBridgePI::QCopBridgePI( int socket, QObject *parent, const char* name )
- : QSocket( parent, name )
+QCopBridgePI::QCopBridgePI( int socket, QObject *parent , const char* name )
+ : QSocket( parent, name )
{
setSocket( socket );
peerport = peerPort();
peeraddress = peerAddress();
#ifndef INSECURE
- if ( !accessAuthorized(peeraddress) ) {
- state = Forbidden;
- startTimer( 0 );
- } else
-#endif
+ if ( !SyncAuthentication::isAuthorized(peeraddress) ) {
+ state = Forbidden;
+ startTimer( 0 );
+ } else
+#endif
{
- state = Connected;
- sendSync = FALSE;
- connect( this, SIGNAL( readyRead() ), SLOT( read() ) );
- connect( this, SIGNAL( connectionClosed() ), SLOT( connectionClosed() ) );
-
- send( "220 Qtopia QCop bridge ready!" );
- state = Wait_USER;
-
- // idle timer to close connections when not used anymore
- startTimer( 60000 );
- connected = TRUE;
+ state = Connected;
+ sendSync = FALSE;
+ connect( this, SIGNAL( readyRead() ), SLOT( read() ) );
+ connect( this, SIGNAL( connectionClosed() ), SLOT( connectionClosed() ) );
+
+ QString intro="220 Qtopia ";
+ intro += QPE_VERSION; intro += ";";
+ intro += "challenge="; intro += SyncAuthentication::serverId(); intro += ";";
+ intro += "loginname="; intro += SyncAuthentication::loginName(); intro += ";";
+ intro += "displayname="; intro += SyncAuthentication::ownerName(); intro += ";";
+ send( intro );
+ state = Wait_USER;
+
+ // idle timer to close connections when not used anymore
+ startTimer( 60000 );
+ connected = TRUE;
}
}
QCopBridgePI::~QCopBridgePI()
{
}
@@ -227,194 +259,166 @@ void QCopBridgePI::send( const QString& msg )
QTextStream os( this );
os << msg << endl;
//qDebug( "sending qcop message: %s", msg.latin1() );
}
void QCopBridgePI::read()
{
while ( canReadLine() )
- process( readLine().stripWhiteSpace() );
-}
-
-bool QCopBridgePI::checkUser( const QString& user )
-{
- if ( user.isEmpty() ) return FALSE;
-
- struct passwd *pw;
- pw = getpwuid( geteuid() );
- QString euser = QString::fromLocal8Bit( pw->pw_name );
- return user == euser;
-}
-
-bool QCopBridgePI::checkPassword( const QString& password )
-{
- // ### HACK for testing on local host
- return true;
-
- /*
- struct passwd *pw = 0;
- struct spwd *spw = 0;
-
- pw = getpwuid( geteuid() );
- spw = getspnam( pw->pw_name );
-
- QString cpwd = QString::fromLocal8Bit( pw->pw_passwd );
- if ( cpwd == "x" && spw )
- cpwd = QString::fromLocal8Bit( spw->sp_pwdp );
-
- QString cpassword = QString::fromLocal8Bit( crypt( password.local8Bit(), cpwd.local8Bit() ) );
- return cpwd == cpassword;
-*/
+ process( readLine().stripWhiteSpace() );
}
void QCopBridgePI::process( const QString& message )
{
//qDebug( "Command: %s", message.latin1() );
// split message using "," as separator
QStringList msg = QStringList::split( " ", message );
if ( msg.isEmpty() ) return;
// command token
QString cmd = msg[0].upper();
// argument token
QString arg;
if ( msg.count() >= 2 )
- arg = msg[1];
-
+ arg = msg[1];
+
// we always respond to QUIT, regardless of state
if ( cmd == "QUIT" ) {
- send( "211 Have a nice day!" );
- delete this;
- return;
+ send( "211 Have a nice day!" );
+ delete this;
+ return;
}
// connected to client
if ( Connected == state )
- return;
+ return;
// waiting for user name
if ( Wait_USER == state ) {
- if ( cmd != "USER" || msg.count() < 2 || !checkUser( arg ) ) {
- send( "530 Please login with USER and PASS" );
- return;
- }
- send( "331 User name ok, need password" );
- state = Wait_PASS;
- return;
+ if ( cmd != "USER" || msg.count() < 2 || !SyncAuthentication::checkUser( arg ) ) {
+ send( "530 Please login with USER and PASS" );
+ return;
+ }
+ send( "331 User name ok, need password" );
+ state = Wait_PASS;
+ return;
}
// waiting for password
if ( Wait_PASS == state ) {
- if ( cmd != "PASS" || !checkPassword( arg ) ) {
- //if ( cmd != "PASS" || msg.count() < 2 || !checkPassword( arg ) ) {
- send( "530 Please login with USER and PASS" );
- return;
- }
- send( "230 User logged in, proceed" );
- state = Ready;
- if ( sendSync ) {
- sendDesktopMessage( "startSync()" );
- sendSync = FALSE;
- }
- return;
+ if ( cmd != "PASS" || !SyncAuthentication::checkPassword( arg ) ) {
+ send( "530 Please login with USER and PASS" );
+ return;
+ }
+ send( "230 User logged in, proceed" );
+ state = Ready;
+ if ( sendSync ) {
+ sendDesktopMessage( "startSync()" );
+ sendSync = FALSE;
+ }
+ return;
}
// noop (NOOP)
else if ( cmd == "NOOP" ) {
- connected = TRUE;
- send( "200 Command okay" );
+ connected = TRUE;
+ send( "200 Command okay" );
}
-
+
// call (CALL)
else if ( cmd == "CALL" ) {
- // example: call QPE/System execute(QString) addressbook
-
- if ( msg.count() < 3 ) {
- send( "500 Syntax error, command unrecognized" );
- }
- else {
-
- QString channel = msg[1];
- QString command = msg[2];
-
- command.stripWhiteSpace();
-
- int paren = command.find( "(" );
- if ( paren <= 0 ) {
- send( "500 Syntax error, command unrecognized" );
- return;
- }
-
- QString params = command.mid( paren + 1 );
- if ( params[params.length()-1] != ')' ) {
- send( "500 Syntax error, command unrecognized" );
- return;
- }
-
- params.truncate( params.length()-1 );
- QByteArray buffer;
- QDataStream ds( buffer, IO_WriteOnly );
-
- int msgId = 3;
-
- QStringList paramList = QStringList::split( ",", params );
- if ( paramList.count() > msg.count() - 3 ) {
- send( "500 Syntax error, command unrecognized" );
- return;
- }
-
- for ( QStringList::Iterator it = paramList.begin(); it != paramList.end(); ++it ) {
-
- QString arg = msg[msgId];
- arg.replace( QRegExp("&0x20;"), " " );
- arg.replace( QRegExp("&amp;"), "&" );
- arg.replace( QRegExp("&0x0d;"), "\n" );
- arg.replace( QRegExp("&0x0a;"), "\r" );
- if ( *it == "QString" )
- ds << arg;
- else if ( *it == "QCString" )
- ds << arg.local8Bit();
- else if ( *it == "int" )
- ds << arg.toInt();
- else if ( *it == "bool" )
- ds << arg.toInt();
- else {
- send( "500 Syntax error, command unrecognized" );
- return;
- }
- msgId++;
- }
-
- if ( !QCopChannel::isRegistered( channel.latin1() ) ) {
- // send message back about it
- QString answer = "599 ChannelNotRegistered " + channel;
- send( answer );
- return;
- }
-
- if ( paramList.count() )
- QCopChannel::send( channel.latin1(), command.latin1(), buffer );
- else
- QCopChannel::send( channel.latin1(), command.latin1() );
-
- send( "200 Command okay" );
- }
+ // example: call QPE/System execute(QString) addressbook
+
+ if ( msg.count() < 3 ) {
+ send( "500 Syntax error, command unrecognized" );
+ }
+ else {
+
+ QString channel = msg[1];
+ QString command = msg[2];
+
+ command.stripWhiteSpace();
+
+ int paren = command.find( "(" );
+ if ( paren <= 0 ) {
+ send( "500 Syntax error, command unrecognized" );
+ return;
+ }
+
+ QString params = command.mid( paren + 1 );
+ if ( params[params.length()-1] != ')' ) {
+ send( "500 Syntax error, command unrecognized" );
+ return;
+ }
+
+ params.truncate( params.length()-1 );
+ QByteArray buffer;
+ QDataStream ds( buffer, IO_WriteOnly );
+
+ int msgId = 3;
+
+ QStringList paramList = QStringList::split( ",", params );
+ if ( paramList.count() > msg.count() - 3 ) {
+ send( "500 Syntax error, command unrecognized" );
+ return;
+ }
+
+ for ( QStringList::Iterator it = paramList.begin(); it != paramList.end(); ++it ) {
+
+ QString arg = msg[msgId];
+ arg.replace( QRegExp("&0x20;"), " " );
+ arg.replace( QRegExp("&amp;"), "&" );
+ arg.replace( QRegExp("&0x0d;"), "\n" );
+ arg.replace( QRegExp("&0x0a;"), "\r" );
+ if ( *it == "QString" )
+ ds << arg;
+ else if ( *it == "QCString" )
+ ds << arg.local8Bit();
+ else if ( *it == "int" )
+ ds << arg.toInt();
+ else if ( *it == "bool" )
+ ds << arg.toInt();
+ else {
+ send( "500 Syntax error, command unrecognized" );
+ return;
+ }
+ msgId++;
+ }
+
+#ifndef QT_NO_COP
+ if ( !QCopChannel::isRegistered( channel.latin1() ) ) {
+ // send message back about it
+ QString answer = "599 ChannelNotRegistered " + channel;
+ send( answer );
+ return;
+ }
+#endif
+
+#ifndef QT_NO_COP
+ if ( paramList.count() )
+ QCopChannel::send( channel.latin1(), command.latin1(), buffer );
+ else
+ QCopChannel::send( channel.latin1(), command.latin1() );
+
+ send( "200 Command okay" );
+#endif
+ }
}
// not implemented
else
- send( "502 Command not implemented" );
+ send( "502 Command not implemented" );
}
void QCopBridgePI::timerEvent( QTimerEvent * )
{
if ( connected )
- connected = FALSE;
+ connected = FALSE;
else
- connectionClosed();
+ connectionClosed();
}
diff --git a/core/launcher/qcopbridge.h b/core/launcher/qcopbridge.h
index 114b3ee..408d10d 100644
--- a/core/launcher/qcopbridge.h
+++ b/core/launcher/qcopbridge.h
@@ -1,12 +1,12 @@
/**********************************************************************
-** Copyright (C) 2000 Trolltech AS. All rights reserved.
+** Copyright (C) 2000-2002 Trolltech AS. All rights reserved.
**
-** This file is part of Qtopia Environment.
+** This file is part of the Qtopia Environment.
**
** This file may be distributed and/or modified under the terms of the
** GNU General Public License version 2 as published by the Free Software
** Foundation and appearing in the file LICENSE.GPL included in the
** packaging of this file.
**
** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
@@ -74,19 +74,16 @@ signals:
protected slots:
void read();
void send( const QString& msg );
void process( const QString& command );
void connectionClosed();
protected:
- bool checkUser( const QString& user );
- bool checkPassword( const QString& pw );
-
void timerEvent( QTimerEvent *e );
private:
State state;
Q_UINT16 peerport;
QHostAddress peeraddress;
bool connected;
bool sendSync;
diff --git a/core/launcher/transferserver.cpp b/core/launcher/transferserver.cpp
index 7294f9c..a6dab07 100644
--- a/core/launcher/transferserver.cpp
+++ b/core/launcher/transferserver.cpp
@@ -1,12 +1,12 @@
/**********************************************************************
-** Copyright (C) 2000 Trolltech AS. All rights reserved.
+** Copyright (C) 2000-2002 Trolltech AS. All rights reserved.
**
-** This file is part of Qtopia Environment.
+** This file is part of the Qtopia Environment.
**
** This file may be distributed and/or modified under the terms of the
** GNU General Public License version 2 as published by the Free Software
** Foundation and appearing in the file LICENSE.GPL included in the
** packaging of this file.
**
** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
@@ -17,40 +17,53 @@
** not clear to you.
**
**********************************************************************/
#define _XOPEN_SOURCE
#include <pwd.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
+#include <time.h>
+#include <shadow.h>
+
+extern "C" {
+#include <uuid/uuid.h>
+#define UUID_H_INCLUDED
+}
#if defined(_OS_LINUX_)
#include <shadow.h>
#endif
#include <qdir.h>
#include <qfile.h>
#include <qtextstream.h>
#include <qdatastream.h>
#include <qmessagebox.h>
#include <qstringlist.h>
#include <qfileinfo.h>
#include <qregexp.h>
//#include <qpe/qcopchannel_qws.h>
#include <qpe/process.h>
+#include <qpe/global.h>
#include <qpe/config.h>
+#include <qpe/contact.h>
+#include <qpe/quuid.h>
+#include <qpe/version.h>
+#ifdef QWS
#include <qpe/qcopenvelope_qws.h>
+#endif
#include "transferserver.h"
#include "qprocess.h"
const int block_size = 51200;
-TransferServer::TransferServer( Q_UINT16 port, QObject *parent,
+TransferServer::TransferServer( Q_UINT16 port, QObject *parent ,
const char* name )
: QServerSocket( port, 1, parent, name )
{
if ( !ok() )
qWarning( "Failed to bind to port %d", port );
}
TransferServer::~TransferServer()
@@ -58,59 +71,165 @@ TransferServer::~TransferServer()
}
void TransferServer::newConnection( int socket )
{
(void) new ServerPI( socket, this );
}
-bool accessAuthorized(QHostAddress peeraddress)
+QString SyncAuthentication::serverId()
{
Config cfg("Security");
cfg.setGroup("Sync");
- uint auth_peer = cfg.readNumEntry("auth_peer",0xc0a80100);
+ QString r=cfg.readEntry("serverid");
+ if ( r.isEmpty() ) {
+ uuid_t uuid;
+ uuid_generate( uuid );
+ cfg.writeEntry("serverid",(r = QUuid( uuid ).toString()));
+ }
+ return r;
+}
+
+QString SyncAuthentication::ownerName()
+{
+ QString vfilename = Global::applicationFileName("addressbook",
+ "businesscard.vcf");
+ if (QFile::exists(vfilename)) {
+ Contact c;
+ c = Contact::readVCard( vfilename )[0];
+ return c.fullName();
+ }
+
+ return "";
+}
+
+QString SyncAuthentication::loginName()
+{
+ struct passwd *pw;
+ pw = getpwuid( geteuid() );
+ return QString::fromLocal8Bit( pw->pw_name );
+}
+
+int SyncAuthentication::isAuthorized(QHostAddress peeraddress)
+{
+ Config cfg("Security");
+ cfg.setGroup("Sync");
+ QString allowedstr = cfg.readEntry("auth_peer","192.168.1.0");
+ QHostAddress allowed;
+ allowed.setAddress(allowedstr);
+ uint auth_peer = allowed.ip4Addr();
uint auth_peer_bits = cfg.readNumEntry("auth_peer_bits",24);
- bool ok = (peeraddress.ip4Addr() & (((1<<auth_peer_bits)-1)<<(32-auth_peer_bits)))
- == auth_peer;
- /* Allows denial-of-service attack.
- if ( !ok ) {
- QMessageBox::warning(0,tr("Security"),
- tr("<p>An attempt to access this device from %1 has been denied.")
- .arg(peeraddress.toString()));
- }
- */
- return ok;
+ uint mask = auth_peer_bits >= 32 // shifting by 32 is not defined
+ ? 0xffffffff : (((1<<auth_peer_bits)-1)<<(32-auth_peer_bits));
+ return (peeraddress.ip4Addr() & mask) == auth_peer;
+}
+
+bool SyncAuthentication::checkUser( const QString& user )
+{
+ if ( user.isEmpty() ) return FALSE;
+ QString euser = loginName();
+ return user == euser;
}
-ServerPI::ServerPI( int socket, QObject *parent, const char* name )
+bool SyncAuthentication::checkPassword( const QString& password )
+{
+#ifdef ALLOW_UNIX_USER_FTP
+ // First, check system password...
+
+ struct passwd *pw = 0;
+ struct spwd *spw = 0;
+
+ pw = getpwuid( geteuid() );
+ spw = getspnam( pw->pw_name );
+
+ QString cpwd = QString::fromLocal8Bit( pw->pw_passwd );
+ if ( cpwd == "x" && spw )
+ cpwd = QString::fromLocal8Bit( spw->sp_pwdp );
+
+ // Note: some systems use more than crypt for passwords.
+ QString cpassword = QString::fromLocal8Bit( crypt( password.local8Bit(), cpwd.local8Bit() ) );
+ if ( cpwd == cpassword )
+ return TRUE;
+#endif
+
+ static int lastdenial=0;
+ static int denials=0;
+ int now = time(0);
+
+ // Detect old Qtopia Desktop (no password)
+ if ( password.isEmpty() ) {
+ if ( denials < 1 || now > lastdenial+600 ) {
+ QMessageBox::warning( 0,tr("Sync Connection"),
+ tr("<p>An unauthorized system is requesting access to this device."
+ "<p>If you are using a version of Qtopia Desktop older than 1.5.1, "
+ "please upgrade."),
+ tr("Deny") );
+ denials++;
+ lastdenial=now;
+ }
+ return FALSE;
+ }
+
+ // Second, check sync password...
+ if ( password.left(6) == "Qtopia" ) {
+ QString cpassword = QString::fromLocal8Bit( crypt( password.mid(8).local8Bit(), "qp" ) );
+ Config cfg("Security");
+ cfg.setGroup("Sync");
+ QString pwds = cfg.readEntry("Passwords");
+ if ( QStringList::split(QChar(' '),pwds).contains(cpassword) )
+ return TRUE;
+
+ // Unrecognized system. Be careful...
+
+ if ( (denials > 2 && now < lastdenial+600)
+ || QMessageBox::warning(0,tr("Sync Connection"),
+ tr("<p>An unrecognized system is requesting access to this device."
+ "<p>If you have just initiated a Sync for the first time, this is normal."),
+ tr("Allow"),tr("Deny"))==1 )
+ {
+ denials++;
+ lastdenial=now;
+ return FALSE;
+ } else {
+ denials=0;
+ cfg.writeEntry("Passwords",pwds+" "+cpassword);
+ return TRUE;
+ }
+ }
+
+ return FALSE;
+}
+
+
+ServerPI::ServerPI( int socket, QObject *parent , const char* name )
: QSocket( parent, name ) , dtp( 0 ), serversocket( 0 ), waitsocket( 0 )
{
state = Connected;
setSocket( socket );
peerport = peerPort();
peeraddress = peerAddress();
#ifndef INSECURE
- if ( !accessAuthorized(peeraddress) ) {
+ if ( !SyncAuthentication::isAuthorized(peeraddress) ) {
state = Forbidden;
startTimer( 0 );
} else
#endif
{
connect( this, SIGNAL( readyRead() ), SLOT( read() ) );
connect( this, SIGNAL( connectionClosed() ), SLOT( connectionClosed() ) );
passiv = FALSE;
for( int i = 0; i < 4; i++ )
wait[i] = FALSE;
- send( "220 Qtopia transfer service ready!" );
+ send( "220 Qtopia " QPE_VERSION " FTP Server" );
state = Wait_USER;
dtp = new ServerDTP( this );
connect( dtp, SIGNAL( completed() ), SLOT( dtpCompleted() ) );
connect( dtp, SIGNAL( failed() ), SLOT( dtpFailed() ) );
connect( dtp, SIGNAL( error( int ) ), SLOT( dtpError( int ) ) );
@@ -146,47 +265,16 @@ void ServerPI::send( const QString& msg )
}
void ServerPI::read()
{
while ( canReadLine() )
process( readLine().stripWhiteSpace() );
}
-bool ServerPI::checkUser( const QString& user )
-{
- if ( user.isEmpty() ) return FALSE;
-
- struct passwd *pw;
- pw = getpwuid( geteuid() );
- QString euser = QString::fromLocal8Bit( pw->pw_name );
- return user == euser;
-}
-
-bool ServerPI::checkPassword( const QString& /* password */ )
-{
- // ### HACK for testing on local host
- return true;
-
- /*
- struct passwd *pw = 0;
- struct spwd *spw = 0;
-
- pw = getpwuid( geteuid() );
- spw = getspnam( pw->pw_name );
-
- QString cpwd = QString::fromLocal8Bit( pw->pw_passwd );
- if ( cpwd == "x" && spw )
- cpwd = QString::fromLocal8Bit( spw->sp_pwdp );
-
- QString cpassword = QString::fromLocal8Bit( crypt( password.local8Bit(), cpwd.local8Bit() ) );
- return cpwd == cpassword;
-*/
-}
-
bool ServerPI::checkReadFile( const QString& file )
{
QString filename;
if ( file[0] != "/" )
filename = directory.path() + "/" + file;
else
filename = file;
@@ -249,30 +337,29 @@ void ServerPI::process( const QString& message )
// connected to client
if ( Connected == state )
return;
// waiting for user name
if ( Wait_USER == state ) {
- if ( cmd != "USER" || msg.count() < 2 || !checkUser( arg ) ) {
+ if ( cmd != "USER" || msg.count() < 2 || !SyncAuthentication::checkUser( arg ) ) {
send( "530 Please login with USER and PASS" );
return;
}
send( "331 User name ok, need password" );
state = Wait_PASS;
return;
}
// waiting for password
if ( Wait_PASS == state ) {
- if ( cmd != "PASS" || !checkPassword( arg ) ) {
- //if ( cmd != "PASS" || msg.count() < 2 || !checkPassword( arg ) ) {
+ if ( cmd != "PASS" || !SyncAuthentication::checkPassword( arg ) ) {
send( "530 Please login with USER and PASS" );
return;
}
send( "230 User logged in, proceed" );
state = Ready;
return;
}
@@ -449,20 +536,23 @@ void ServerPI::process( const QString& message )
}
// delete (DELE)
else if ( cmd == "DELE" ) {
if ( args.isEmpty() )
send( "500 Syntax error, command unrecognized" );
else {
QFile file( absFilePath( args ) ) ;
- if ( file.remove() )
+ if ( file.remove() ) {
send( "250 Requested file action okay, completed" );
- else
+ QCopEnvelope e("QPE/System", "linkChanged(QString)" );
+ e << file.name();
+ } else {
send( "550 Requested action not taken" );
+ }
}
}
// remove directory (RMD)
else if ( cmd == "RMD" ) {
if ( args.isEmpty() )
send( "500 Syntax error, command unrecognized" );
else {
@@ -629,19 +719,26 @@ bool ServerPI::parsePort( const QString& pp )
peeraddress = QHostAddress( ( p[0].toInt() << 24 ) + ( p[1].toInt() << 16 ) +
( p[2].toInt() << 8 ) + p[3].toInt() );
peerport = ( p[4].toInt() << 8 ) + p[5].toInt();
return TRUE;
}
void ServerPI::dtpCompleted()
{
- dtp->close();
- waitsocket = 0;
send( "226 Closing data connection, file transfer successful" );
+ if ( dtp->dtpMode() == ServerDTP::RetrieveFile ) {
+ QString fn = dtp->fileName();
+ if ( fn.right(8)==".desktop" && fn.find("/Documents/")>=0 ) {
+ QCopEnvelope e("QPE/System", "linkChanged(QString)" );
+ e << fn;
+ }
+ }
+ waitsocket = 0;
+ dtp->close();
}
void ServerPI::dtpFailed()
{
dtp->close();
waitsocket = 0;
send( "451 Requested action aborted: local error in processing" );
}
@@ -847,17 +944,17 @@ QString ServerPI::absFilePath( const QString& file )
void ServerPI::timerEvent( QTimerEvent * )
{
connectionClosed();
}
-ServerDTP::ServerDTP( QObject *parent, const char* name )
+ServerDTP::ServerDTP( QObject *parent = 0, const char* name = 0)
: QSocket( parent, name ), mode( Idle ), createTargzProc( 0 ),
retrieveTargzProc( 0 ), gzipProc( 0 )
{
connect( this, SIGNAL( connected() ), SLOT( connected() ) );
connect( this, SIGNAL( connectionClosed() ), SLOT( connectionClosed() ) );
connect( this, SIGNAL( bytesWritten( int ) ), SLOT( bytesWritten( int ) ) );
connect( this, SIGNAL( readyRead() ), SLOT( readyRead() ) );
@@ -886,18 +983,20 @@ ServerDTP::~ServerDTP()
buf.close();
file.close();
createTargzProc->kill();
}
void ServerDTP::extractTarDone()
{
qDebug("extract done");
+#ifndef QT_NO_COP
QCopEnvelope e( "QPE/Desktop", "restoreDone(QString)" );
e << file.name();
+#endif
}
void ServerDTP::connected()
{
// send file mode
switch ( mode ) {
case SendFile :
if ( !file.exists() || !file.open( IO_ReadOnly) ) {
diff --git a/core/launcher/transferserver.h b/core/launcher/transferserver.h
index 076e460..a3bb060 100644
--- a/core/launcher/transferserver.h
+++ b/core/launcher/transferserver.h
@@ -1,12 +1,12 @@
/**********************************************************************
-** Copyright (C) 2000 Trolltech AS. All rights reserved.
+** Copyright (C) 2000-2002 Trolltech AS. All rights reserved.
**
-** This file is part of Qtopia Environment.
+** This file is part of the Qtopia Environment.
**
** This file may be distributed and/or modified under the terms of the
** GNU General Public License version 2 as published by the Free Software
** Foundation and appearing in the file LICENSE.GPL included in the
** packaging of this file.
**
** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
@@ -31,16 +31,30 @@ class TransferServer : public QServerSocket
public:
TransferServer( Q_UINT16 port, QObject *parent = 0, const char* name = 0 );
virtual ~TransferServer();
void newConnection( int socket );
};
+class SyncAuthentication : QObject
+{
+ Q_OBJECT
+
+public:
+ static int isAuthorized(QHostAddress peeraddress);
+ static bool checkPassword(const QString& pw);
+ static bool checkUser(const QString& user);
+
+ static QString serverId();
+ static QString loginName();
+ static QString ownerName();
+};
+
class ServerDTP : public QSocket
{
Q_OBJECT
public:
ServerDTP( QObject *parent = 0, const char* name = 0 );
~ServerDTP();
@@ -60,16 +74,17 @@ public:
void retrieveFile( const QString fn, const QHostAddress& host, Q_UINT16 port );
void retrieveGzipFile( const QString &fn );
void retrieveGzipFile( const QString &fn, const QHostAddress& host, Q_UINT16 port );
void retrieveByteArray();
void retrieveByteArray( const QHostAddress& host, Q_UINT16 port );
Mode dtpMode() { return mode; }
QByteArray buffer() { return buf.buffer(); }
+ QString fileName() const { return file.name(); }
void setSocket( int socket );
signals:
void completed();
void failed();
private slots:
@@ -126,18 +141,16 @@ protected slots:
void process( const QString& command );
void connectionClosed();
void dtpCompleted();
void dtpFailed();
void dtpError( int );
void newConnection( int socket );
protected:
- bool checkUser( const QString& user );
- bool checkPassword( const QString& pw );
bool checkReadFile( const QString& file );
bool checkWriteFile( const QString& file );
bool parsePort( const QString& pw );
bool backupRestoreGzip( const QString &file, QStringList &targets );
bool backupRestoreGzip( const QString &file );
bool sendList( const QString& arg );
void sendFile( const QString& file );
@@ -159,10 +172,8 @@ private:
ServerSocket *serversocket;
QString waitfile;
QDir directory;
QByteArray waitarray;
QString renameFrom;
QString lastCommand;
int waitsocket;
};
-
-bool accessAuthorized(QHostAddress peeraddress);