semaphore reading qstring example error
-
Hello guys,
i am trying to use the semaphores shared memory to read a QString value. I am attaching my code. I can block the memory and detect it being blocked but can not read the value from the shared memory.thanks in advance for assistance
#include "mainwindow.h" #include <QApplication> #include <QSystemSemaphore> #include <QSharedMemory> #include <QMessageBox> #include <QString> #include <QBuffer> #include <QtGlobal> int main(int argc, char *argv[]) { QApplication a(argc, argv); QSystemSemaphore semaphore("<uniq id>", 1); // create semaphore semaphore.acquire(); // Raise the semaphore, barring other instances to work with shared memory #ifndef Q_OS_WIN32 // in linux / unix shared memory is not freed when the application terminates abnormally, // so you need to get rid of the garbage QSharedMemory nix_fix_shared_memory("<uniq id 2>"); if(nix_fix_shared_memory.attach()){ nix_fix_shared_memory.detach(); } #endif QSharedMemory sharedMemory("<uniq id 2>"); // Create a copy of the shared memory bool is_running; // variable to test the already running application QBuffer buffer; int x=0; QString ux; QDataStream in(&buffer); if (sharedMemory.attach()){ // We are trying to attach a copy of the shared memory // To an existing segment is_running = true; // If successful, it determines that there is already a running instance sharedMemory.lock(); buffer.setData((char*)sharedMemory.constData(), sharedMemory.size()); buffer.open(QBuffer::ReadOnly); char *from = (char*)sharedMemory.data(); memcpy (from, &ux, sharedMemory.size()); //in >> ux; sharedMemory.unlock(); }else{ buffer.open(QBuffer::ReadWrite); QDataStream out(&buffer); sharedMemory.create(2); // Otherwise allocate 1 byte of memory out << QString("Y"); sharedMemory.lock(); char *to = (char*)sharedMemory.data(); const char *from = buffer.data().data(); int size=buffer.size(); memcpy(to, from, qMin(sharedMemory.size(), size)); sharedMemory.unlock(); //out << (int)1; is_running = false; // And determines that another instance is not running } semaphore.release(); // If you already run one instance of the application, then we inform the user about it // and complete the current instance of the application if(is_running){ QMessageBox msgBox; QString u = QString::number(x); msgBox.setIcon(QMessageBox::Warning); msgBox.setText("The application is already running.\n" "value " + ux); msgBox.exec(); return 1; } MainWindow w; w.show(); return a.exec(); }
-
You are aware of QtSingleApplication, right? https://github.com/qtproject/qt-solutions/tree/master/qtsingleapplication
And a string can be (simpler) saved to and read from a file (for example using QSettings).
Which is another way of saying "I've never used QSystemSemaphore or QSharedMemory and don't know how to help you" ;-)
-
You are aware of QtSingleApplication, right? https://github.com/qtproject/qt-solutions/tree/master/qtsingleapplication
And a string can be (simpler) saved to and read from a file (for example using QSettings).
Which is another way of saying "I've never used QSystemSemaphore or QSharedMemory and don't know how to help you" ;-)
@sierdzio I need to exchange data between different applications
-
Hi,
What exactly are you trying to exchange between the two applications ?
-
i am trying to exchange a string. Actually i wanted to create a slot in app B that responds to a signal from App A and tried to do it with semaphore but i think this is not the correct approach. I think doing it with dBus may be better or using local network is also another approach.
-
i am trying to exchange a string. Actually i wanted to create a slot in app B that responds to a signal from App A and tried to do it with semaphore but i think this is not the correct approach. I think doing it with dBus may be better or using local network is also another approach.
@SherifOmran said in semaphore reading qstring example error:
I think doing it with dBus may be better or using local network is also another approach.
There is also the (quite new) QtRemoteObjects module.
-
@sierdzio : do you know if there is an example to do it?
thank you -
Hi
Just as a note this sample does work
https://doc.qt.io/qt-5/qtcore-ipc-sharedmemory-example.html -
Hello guys,
i am trying to use the semaphores shared memory to read a QString value. I am attaching my code. I can block the memory and detect it being blocked but can not read the value from the shared memory.thanks in advance for assistance
#include "mainwindow.h" #include <QApplication> #include <QSystemSemaphore> #include <QSharedMemory> #include <QMessageBox> #include <QString> #include <QBuffer> #include <QtGlobal> int main(int argc, char *argv[]) { QApplication a(argc, argv); QSystemSemaphore semaphore("<uniq id>", 1); // create semaphore semaphore.acquire(); // Raise the semaphore, barring other instances to work with shared memory #ifndef Q_OS_WIN32 // in linux / unix shared memory is not freed when the application terminates abnormally, // so you need to get rid of the garbage QSharedMemory nix_fix_shared_memory("<uniq id 2>"); if(nix_fix_shared_memory.attach()){ nix_fix_shared_memory.detach(); } #endif QSharedMemory sharedMemory("<uniq id 2>"); // Create a copy of the shared memory bool is_running; // variable to test the already running application QBuffer buffer; int x=0; QString ux; QDataStream in(&buffer); if (sharedMemory.attach()){ // We are trying to attach a copy of the shared memory // To an existing segment is_running = true; // If successful, it determines that there is already a running instance sharedMemory.lock(); buffer.setData((char*)sharedMemory.constData(), sharedMemory.size()); buffer.open(QBuffer::ReadOnly); char *from = (char*)sharedMemory.data(); memcpy (from, &ux, sharedMemory.size()); //in >> ux; sharedMemory.unlock(); }else{ buffer.open(QBuffer::ReadWrite); QDataStream out(&buffer); sharedMemory.create(2); // Otherwise allocate 1 byte of memory out << QString("Y"); sharedMemory.lock(); char *to = (char*)sharedMemory.data(); const char *from = buffer.data().data(); int size=buffer.size(); memcpy(to, from, qMin(sharedMemory.size(), size)); sharedMemory.unlock(); //out << (int)1; is_running = false; // And determines that another instance is not running } semaphore.release(); // If you already run one instance of the application, then we inform the user about it // and complete the current instance of the application if(is_running){ QMessageBox msgBox; QString u = QString::number(x); msgBox.setIcon(QMessageBox::Warning); msgBox.setText("The application is already running.\n" "value " + ux); msgBox.exec(); return 1; } MainWindow w; w.show(); return a.exec(); }
I can block the memory and detect it being blocked but can not read the value from the shared memory.
If you want to do it your way, and if I read your code right:
QString ux; char *from = (char*)sharedMemory.data(); memcpy (from, &ux, sharedMemory.size());
This writes to the shared memory area, named
from
, from theQString
, which is empty.If I didn't know better, I'd wonder whether you simply have your arguments to
memcpy()
the wrong way round; don't you intend:memcpy (&ux, from, sharedMemory.size());
This is in the code which attaches to a segment already created by your other, creation route, so I presume it's supposed to be reading into the
QString
what the other route left there. [Meanwhile I imagine you're not supposed to write directly into aQString
like this, so it may well go wrong in that sense, but that's a different matter...]