author | mickeyl <mickeyl> | 2006-05-02 08:57:25 (UTC) |
---|---|---|
committer | mickeyl <mickeyl> | 2006-05-02 08:57:25 (UTC) |
commit | d5b6868cb4f99d2c3dc3587115cd37c09e4610eb (patch) (side-by-side diff) | |
tree | 1397f12f885c849419e511ad203d19696c4ae07e /core | |
parent | 1295db77f2ab7e9125183e4240de0b92f72940e4 (diff) | |
download | opie-d5b6868cb4f99d2c3dc3587115cd37c09e4610eb.zip opie-d5b6868cb4f99d2c3dc3587115cd37c09e4610eb.tar.gz opie-d5b6868cb4f99d2c3dc3587115cd37c09e4610eb.tar.bz2 |
bluetooth patches courtesy Dmitriy Korovkin (thanks!):
* When sending data to a device, do service discovery in order to get port number.
* Switched to ussp-push for sending.
* Clear receivers list on rescan.
* Changed the way of window closing in order to shut down IRDA and bluetooth correctly.
-rw-r--r-- | core/obex/btobex.cpp | 79 | ||||
-rw-r--r-- | core/obex/btobex.h | 8 | ||||
-rw-r--r-- | core/obex/obex.pro | 4 | ||||
-rw-r--r-- | core/obex/obexsend.cpp | 18 |
4 files changed, 87 insertions, 22 deletions
diff --git a/core/obex/btobex.cpp b/core/obex/btobex.cpp index a2866f6..bb5c06d 100644 --- a/core/obex/btobex.cpp +++ b/core/obex/btobex.cpp @@ -1,20 +1,24 @@ #include "btobex.h" +#include <manager.h> +#include <services.h> /* OPIE */ #include <opie2/oprocess.h> #include <opie2/odebug.h> /* QT */ #include <qfileinfo.h> - - +#include <qstring.h> +#include <qmap.h> +#include <qmessagebox.h> using namespace OpieObex; using namespace Opie::Core; /* TRANSLATOR OpieObex::Obex */ +using namespace OpieTooth; BtObex::BtObex( QObject *parent, const char* name ) : QObject(parent, name ) { @@ -25,13 +29,18 @@ BtObex::BtObex( QObject *parent, const char* name ) connect( this, SIGNAL(error(int) ), // for recovering to receive SLOT(slotError() ) ); connect( this, SIGNAL(sent(bool) ), SLOT(slotError() ) ); + btManager = NULL; }; + BtObex::~BtObex() { + if (btManager) + delete btManager; delete m_rec; delete m_send; } + void BtObex::receive() { m_receive = true; m_outp = QString::null; m_rec = new OProcess(); @@ -67,35 +76,80 @@ void BtObex::send( const QString& fileName, const QString& bdaddr) { emit error( -1 ); // we did not delete yet but it's not running slotExited is pending return; } } + //Now we need to find out if the OBEX push is supported for this device + //And get the port number + if (!btManager) { + btManager = new Manager("hci0"); + connect(btManager, + SIGNAL(foundServices(const QString&, Services::ValueList)), + this, SLOT(slotFoundServices(const QString&, Services::ValueList))); + } + btManager->searchServices(bdaddr); +} + +/** + * This function reacts on the service discovery finish + */ +void BtObex::slotFoundServices(const QString&, Services::ValueList svcList) +{ + QValueList<OpieTooth::Services>::Iterator it; + QMap<int, QString> classList; //The classes list + QMap<int, QString>::Iterator classIt; //Iterator in the class list + int portNum = -1; //The desired port number + odebug << "BtObex slotFoundServices" << oendl; + if (svcList.isEmpty()) { + QMessageBox::critical(NULL, tr("Object send"), tr("No services found")); + emit error(-1); + return; + } + for (it = svcList.begin(); it != svcList.end(); it++) { + classList = (*it).classIdList(); + classIt = classList.begin(); + if (classIt == classList.end()) + continue; +////We really need symbolic names for service IDs + //Ok, we have found the object push service + if (classIt.key() == 4357) { + portNum = (*it).protocolDescriptorList().last().port(); + break; + } + } + if (portNum == -1) { + QMessageBox::critical(NULL, tr("Object send"), + tr("No OBEX Push service")); + emit error(-1); + return; + } + m_port = portNum; sendNow(); } + void BtObex::sendNow(){ if ( m_count >= 25 ) { // could not send emit error(-1 ); emit sent(false); return; } // OProcess inititialisation - m_send = new OProcess(); + m_send = new OProcess(0, "ussp-push"); m_send->setWorkingDirectory( QFileInfo(m_file).dirPath(true) ); - // obextool push file <bdaddr> [channel] - // 9 for phones. - // Palm T3 accepts pictures on 1 - *m_send << "obextool" << "push"; + // ussp-push --timeo 30 <btaddr:port> file file + *m_send << "ussp-push" << "--timeo 30"; + *m_send << m_bdaddr + "@" + QString::number(m_port); *m_send << QFile::encodeName(QFileInfo(m_file).fileName()); - *m_send << m_bdaddr << "9"; + *m_send << QFile::encodeName(QFileInfo(m_file).fileName()); + m_send->setUseShell(true); // connect to slots Exited and and StdOut connect(m_send, SIGNAL(processExited(Opie::Core::OProcess*) ), this, SLOT(slotExited(Opie::Core::OProcess*)) ); connect(m_send, SIGNAL(receivedStdout(Opie::Core::OProcess*, char*, int )), this, SLOT(slotStdOut(Opie::Core::OProcess*, char*, int) ) ); - // now start it - if (!m_send->start(/*OProcess::NotifyOnExit, OProcess::AllOutput*/ ) ) { + if (!m_send->start(OProcess::NotifyOnExit, OProcess::AllOutput) ) { m_count = 25; emit error(-1 ); delete m_send; m_send=0; @@ -105,8 +159,10 @@ void BtObex::sendNow(){ emit currentTry( m_count ); } void BtObex::slotExited(OProcess* proc ){ + odebug << proc->name() << " exited with result " + << proc->exitStatus() << oendl; if (proc == m_rec ) // receive process received(); else if ( proc == m_send ) sendEnd(); @@ -139,9 +195,9 @@ void BtObex::sendEnd() { if ( m_send->exitStatus() == 0 ) { delete m_send; m_send=0; emit sent(true); - }else if (m_send->exitStatus() == 255 ) { // it failed maybe the other side wasn't ready + }else if (m_send->exitStatus() != 0 ) { // it failed maybe the other side wasn't ready // let's try it again delete m_send; m_send = 0; sendNow(); @@ -158,8 +214,9 @@ QString BtObex::parseOut( ){ QString path; QStringList list = QStringList::split("\n", m_outp); QStringList::Iterator it; for (it = list.begin(); it != list.end(); ++it ) { + odebug << (*it) << oendl; if ( (*it).startsWith("Wrote" ) ) { int pos = (*it).findRev('(' ); if ( pos > 0 ) { diff --git a/core/obex/btobex.h b/core/obex/btobex.h index 5ab591c..099f04a 100644 --- a/core/obex/btobex.h +++ b/core/obex/btobex.h @@ -3,11 +3,14 @@ #ifndef OpieBtObex_H #define OpieBtObex_H #include <qobject.h> +#include <services.h> +#include <manager.h> namespace Opie {namespace Core {class OProcess;}} class QCopChannel; +using namespace OpieTooth; namespace OpieObex { // Maybe this should be derved from Obex. class BtObex : public QObject { Q_OBJECT @@ -54,19 +57,22 @@ namespace OpieObex { uint m_count; QString m_file; QString m_outp; QString m_bdaddr; + int m_port; Opie::Core::OProcess *m_send; Opie::Core::OProcess *m_rec; bool m_receive : 1; + OpieTooth::Manager* btManager; void shutDownReceive(); private slots: // the process exited - void slotExited(Opie::Core::OProcess* proc) ; + void slotExited(Opie::Core::OProcess*) ; void slotStdOut(Opie::Core::OProcess*, char*, int); void slotError(); + void slotFoundServices(const QString&, Services::ValueList); private: void sendNow(); QString parseOut(); diff --git a/core/obex/obex.pro b/core/obex/obex.pro index d6b527c..33cb957 100644 --- a/core/obex/obex.pro +++ b/core/obex/obex.pro @@ -4,11 +4,11 @@ HEADERS = obex.h btobex.h obexhandler.h obexsend.h receiver.h obeximpl.h SOURCES = obex.cpp btobex.cpp obexsend.cpp obexhandler.cpp receiver.cpp obeximpl.cpp TARGET = opieobex DESTDIR = $(OPIEDIR)/plugins/obex INTERFACES = obexsendbase.ui -INCLUDEPATH += $(OPIEDIR)/include $(OPIEDIR)/core/launcher +INCLUDEPATH += $(OPIEDIR)/include $(OPIEDIR)/core/launcher $(OPIEDIR)/noncore/net/opietooth/lib DEPENDPATH += -LIBS += -lqpe -lopiecore2 +LIBS += -lopietooth1 -lqpe -lopiecore2 VERSION = 0.0.3 include( $(OPIEDIR)/include.pro ) target.path = $$prefix/plugins/applets diff --git a/core/obex/obexsend.cpp b/core/obex/obexsend.cpp index 9cd9972..dbbb7b3 100644 --- a/core/obex/obexsend.cpp +++ b/core/obex/obexsend.cpp @@ -19,10 +19,10 @@ using namespace Opie::Core; #include <qlabel.h> #include <qpushbutton.h> #include <qpixmap.h> #include <qlistview.h> -#include <qtimer.h> +#include <unistd.h> /* TRANSLATOR OpieObex::SendWidget */ SendWidget::SendWidget( QWidget* parent, const char* name ) : obexSendBase( parent, name ) { @@ -82,9 +82,9 @@ int SendWidget::addReceiver(const char *r, const char *icon) } bool SendWidget::receiverSelected(int id) { - return receivers[id]->pixmap(2); + return (bool)(receivers[id]->pixmap(2) != NULL); } void SendWidget::setReceiverStatus( int id, const QString& status ) { if ( !receivers.contains(id) ) return; @@ -186,9 +186,10 @@ void SendWidget::send_to_receivers() { } void SendWidget::scan_for_receivers() { - //FIXME: Clean ListBox prior to (re)scan + receiverList->clear(); + receivers.clear(); sendButton->setDisabled( true ); if ( !QCopChannel::isRegistered("QPE/IrDaApplet") ) { @@ -225,15 +226,16 @@ void SendWidget::toggle_receiver(QListViewItem* item) } void SendWidget::closeEvent( QCloseEvent* e) { - e->accept(); // make sure - QTimer::singleShot(0, this, SLOT(userDone() ) ); -} -void SendWidget::userDone() { + obexSendBase::closeEvent(e); QCopEnvelope e0("QPE/IrDaApplet", "disableIrda()"); QCopEnvelope e1("QPE/Bluetooth", "disableBluetooth()"); - emit done(); } + +void SendWidget::userDone() { + close(); +} + QString SendWidget::file()const { return m_file; } |