Cannot connect to the device with QSerialPort - c++

I develop Qt application in C++ under manjaro linux. The goal is to connect with a qC (Nucleo-L476RG Board) and receive data from accelerometer. App can find device on /dev/ttyACM0, but when i try to connect it fails with error "QSerialPort::DeviceNotFoundError". Checking errorString() gives "No such file or directory", but it still can find it in /dev.
I'm in the right group to read the file:
[1]: https://i.stack.imgur.com/CG1yZ.png
I use Qt v.6.2.4, but have build the code with Qt v.5.15.3. I tried to run another person's app that does the same and works under ubuntu, but it didn't work.
Here is my code with the searching and connecting methods. Method addToLogs() just prints logs in textEdit.
void MainWindow::addToLogs(QString message)
{
QString currDateTime = QDateTime::currentDateTime().toString("yyyy.MM.dd hh:mm:ss");
ui->textEditLogs->append(currDateTime + "\t" + message);
}
void MainWindow::on_pushButtonSearch_clicked()
{
ui->comboBoxDevices->clear();
this->addToLogs("Szukam urządzeń...");
QList<QSerialPortInfo> devices;
devices = QSerialPortInfo::availablePorts();
if(devices.count() > 0)
{
for(int i=0; i<devices.count(); i++)
{
this->addToLogs(devices.at(i).portName());// + " " + devices.at(i).description());
//ui->comboBoxDevices->addItem(devices.at(i).systemLocation());//portName());
ui->comboBoxDevices->addItem(devices.at(i).portName());
}
}
}
void MainWindow::on_pushButtonConnect_clicked()
{
if(ui->comboBoxDevices->count() == 0)
{
this->addToLogs("Nie wykryto żadnych urządzeń!");
return;
}
if(this->device->isOpen())
{
this->addToLogs("Port jest już otwarty!");
return;
}
QString portName = ui->comboBoxDevices->currentText();
//this->device->setPortName(portName);
this->device->setPortName("/dev/ttyACM0");
qDebug() << this->device->portName();
if(device->open(QSerialPort::ReadWrite))
{
this->device->setBaudRate(QSerialPort::Baud9600);
this->device->setParity(QSerialPort::NoParity);
this->device->setDataBits(QSerialPort::Data8);
this->device->setStopBits(QSerialPort::OneStop);
this->device->setFlowControl(QSerialPort::NoFlowControl);
this->addToLogs("Połączono z urządzeniem " + portName);
}
else
{
this->addToLogs("Otwarcie portu szeregowego się nie powiodło!");
this->addToLogs(device->errorString());
qDebug() << this->device->error();
}
}
I will be thankful for help, cause i've benn sitting on it for last 2 or 3 weeks and nothing works.

Related

QFile write does not respond / crashes the application

I'm working on embedded linux and copying files to usb flash drives.
my files:
sourceFile->open(QIODevice::ReadOnly);
targetFile->open(QIODevice::ReadWrite);
the variables
nCopySize = sourceFile->size() / 100;
QByteArray buffer;
and the read write part:
//copy files
for (int count = 0; !(buffer = sourceFile->read(nCopySize + 1)).isEmpty(); count+=(nCopySize + 1))
{
try {
int writeErr = targetFile->write(buffer);
qDebug() << writeErr;
if (writeErr == -1) { //e.g. when device is plugged off
abortCopyFile = true;
}
} catch (const std::exception& ex) {
qDebug() << "catched something:" << ex.what();
//abort copying file... etc.
} catch (...) {
qDebug() << "catched something else";
//abort copying file... etc.
}
//report progress ...
//abort-option
if (abortCopyFile == true)
break;
}
I don't know if the catch part is right, but that's not my actual question. The point is, that when I unplug the USB flash drive while copying the file from the system to the USB flash drive, the line
targetFile->write(buffer);
sometimes responds -1 and sometimes it responds not at all and the application kinda crashes ominously.
So I thought the try-catch would help me but it doesn't. It does not catch anything. The app just crashes.
What can I do about that problem? Restarting the application is the least I want to do.

QNetworkConfigurationManager::allConfigurations() doesn't list WLAN

Running under Windows 10, tested with two different Systems:
When i run QNetworkConfigurationManager::allConfigurations() I don't get any WLAN configuration, even if I'm connected actively to a Wifi Network.
Header:
public:
NetworkManager(QObject* parent = 0);
private slots:
void onNetworkConfigUpdate();
private:
QNetworkConfiguration cfg;
QList<QNetworkConfiguration> netcfgList;
QNetworkConfigurationManager ncm;
.cpp
NetworkManager::NetworkManager(QObject* parent) : QObject(parent) {
ncm.updateConfigurations();
connect(&ncm, SIGNAL(updateCompleted()), this, SLOT(onNetworkConfigUpdate()));
}
void NetworkManager::onNetworkConfigUpdate() {
netcfgList = ncm.allConfigurations();
for (auto& x : netcfgList) {
if (x.bearerType() == QNetworkConfiguration::BearerWLAN) {
qDebug() << "Wifi found: " << x.name();
} else {
qDebug() << "Something else: " << x.bearerType() << " - name: " << x.name();
}
}
}
Output:
Something else: 0 - name: "Teredo Tunneling Pseudo-Interface"
Something else: 1 - name: "Ethernet"
Something else: 1 - name: "VirtualBox Host-Only Network"
I'm running on Windows 10; Qt 5.9.4 with MSVC2015
I checked with an Intel Wireless Card and an external USB Wifi-Stick. Why is it not showing any WLAN?
I had the same problem. To me was caused by a missing bearer plugin DLL.
To sort this out, I had to copy the QT "plugins/bearer" folder (containing qgenericbearer.dll and qnativewifibearer.dll) in my application root folder.
Like this:
ApplicationFolder/
Application.exe
...
Qt5Network.dll
bearer/
qgenericbearer.dll
qnativewifibearer.dll

boost::filesystem::directory_interatory i(path) crashes on start up in qt creator

for(directory_iterator i(l_path),end_iter; i != end_iter; i++){
string im_name = filename;
//string im_name = i->path().filename().string();
string l_filename = l_path + im_name;
im_name.replace(im_name.begin(),im_name.begin() + 4, string("right"));
string r_filename = r_path + im_name;
Mat lim = imread(l_filename),rim = imread(r_filename);
if(!lim.empty() && !rim.empty()){
l_images.push_back(lim);
r_images.push_back(rim);
}
}
The above crashes on start up and yes the path is there but for some reason it won't run. I have tried this with out the path and it runs. I have no idea what is going wrong. Thanks for any help you can give. below is where i declare it. I am using the latest build of boost and qt creator with open cv to get disparity images for stereo vision, this is what i am using to make the xml file for calibration.
filename = DISTFOLDER + string("stereo_calib.xml");
calib = new calibrator(LEFTFOLDER,RIGHTFOLDER,1.f,5,4,"lImage.png");
calib->calc_image_points(true);
bool done = calib->calibrate();
if(!done){
qDebug("stereo calibration failed");
}
calib->save_info(filename);
Even with try{... }catch blocks it still crashes in QT, I don't know what I changed in my code or the QT environment since it used to work.
Note that when running the app from QT Creator run console it crushes, but running the app directly either from cmd or via explorer works just fine.
The Problem I believe is within QT environment variables being messed up.
The only solution is to append QCoreApplication::applicationDirPath ().toStdString() to the boost::filesystem::directory_iterator iterator(string("tools/adb/"));and make sure the string is what boost expects for path strings.
The try catch block outputs
is_directory failed with The system cannot find the path specified
Here is my current code:
try {
boost::filesystem::directory_iterator iterator(string("tools/adb/"));
for(; iterator != boost::filesystem::directory_iterator(); ++iterator) {
if(is_directory(iterator->path())) {
cout << (iterator->path()) << endl;
adb_s str;
str.path=iterator->path().string();
boost::replace_all(str.path, "/", "\\");
str.path+="\\";
adb_path.push_back(str);
}
}
} catch(const boost::filesystem::filesystem_error& e) {
if(e.code() == boost::system::errc::permission_denied) {
std::cout << "Search permission is denied for one of the directories ";
std::cout << "in the path prefix of \n";
} else {
std::cout << "is_directory failed with ";
std::cout << e.code().message() << '\n';
}
}

Connecting to SQL server 2005 through QT C++

I have a server of windows server 2003 and its IP on my local network is 192.168.1.220
This server has SOL server 2005 express edition installed. This SQL server has a database called amir.
I want to connect to it from a Linux client on the same network.
SQL server service using port 1617 on my server and I used this port to connect to the server using java.
Wow i want to use QT C++ but my code doesn't work.
This is my code:
#include <QtCore/QCoreApplication>
#include <iostream>
#include <QSqldatabase>
#include <QSqldriver>
int main(int argc, char *argv[])
{
QCoreApplication a(argc, argv);
QSqlDatabase db = QSqlDatabase::addDatabase("QODBC");
bool test=db.isValid();//true
test=db.isDriverAvailable("QODBC");//true
db.setHostName("192.168.1.220\\SQLEXPRESS");
db.setDatabaseName("DRIVER={SQL Server};SERVER=192.168.1.220\\SQLEXPRESS:1617;DATABASE=amir");
db.setUserName("sa");
db.setPassword("amir");
db.setPort(1617);
test=db.isValid();//true
if(!db.open())
{
cout<<endl<<"not connected"<<endl;
QString error=db.lastError().text();
cout<<error.toLocal8Bit().data();
return false;
}
else
cout<<endl<<"connected"<<endl;
return true;
}
Every time i try this it out "not connected" and the error is
[unixODBC][Driver Manager]Data source name not found, and no default driver specified QODBC3: Unable to connect
Using these parameters I can connect using java
So what is the wrong here? and if there is another fasting way to connect to the SQL server using qt c++ than ODBC driver.
You need to setup a data source name on your server to connect through ODBC. Here is some code that I use to setup a DSN:
QString SQLServerProvider::buildDSN(QString server, QString database, QString username, QString password)
{
#ifdef Q_WS_MACX
QString dsn = QString("DRIVER=/usr/local/lib/libtdsodbc.so;SERVER=%1;TDS_VERSION=8pClient;DATABASE=%2;PORT=1433;UID=%3;PWD=%4;").arg(server).arg(database).arg(username).arg(password);
#endif
#ifdef Q_WS_X11
QString dsn = QString("DRIVER={FreeTDS};SERVER=%1;TDS_VERSION=8.0;PORT=1433;DATABASE=%2;UID=%3;PWD=%4;").arg(server).arg(database).arg(username).arg(password);
#endif
#ifdef Q_WS_WIN
QString dsn = QString("DRIVER={SQL SERVER};SERVER=%1;DATABASE=%2;UID=%3;PWD=%4;").arg(server).arg(database).arg(username).arg(password);
#endif
return dsn;
}
QSqlDatabase db = QSqlDatabase::addDatabase("QODBC", databaseName);
db.setDatabaseName(buildDSN(server, database, username, password));
Here is some code that I forgot to put in the initial post:
#ifdef Q_WS_X11
QString dir = QDir::homePath();
QDir d;
QString libdir = d.absolutePath();
QFile odbcinst(dir + "/.odbcinst.ini");
if(!odbcinst.exists())
{
odbcinst.open(QIODevice::WriteOnly | QIODevice::Text);
QTextStream out(&odbcinst);
out << "[FreeTDS]\n";
out << "Description = v0.91 with protocol v8.0\n";
out << "Driver = " + libdir + "/libtdsodbc.so\n";
out << "Setup = " + libdir + "/libtdsodbc.so\n";
out << "FileUsage = 1";
odbcinst.close();
}
else
{
QList<QString> lines;
odbcinst.open(QIODevice::ReadOnly | QIODevice::Text);
QTextStream readfile(&odbcinst);
int i = 0, lnbr = 0;
bool found = false;
while(!readfile.atEnd())
{
QString line = readfile.readLine();
if(line.contains("[FreeTDS]"))
{
lnbr = i;
found = true;
}
lines.append(line);
i++;
}
odbcinst.close();
// append to end
if(!found)
{
// append to the end
odbcinst.open(QIODevice::Append | QIODevice::Text);
QTextStream file(&odbcinst);
file << "\n[FreeTDS]\n";
file << "Description = v0.91 with protocol v8.0\n";
file << "Driver = " + libdir + "/libtdsodbc.so\n";
file << "Setup = " + libdir + "/libtdsodbc.so\n";
file << "FileUsage = 1";
odbcinst.close();
}
else // update existing entry
{
qDebug() << "Found an entry for FreeTDS. Updating driver to " + libdir + "/libtdsodbc.so.";
qDebug() << lines[lnbr+2];
qDebug() << lines[lnbr+3];
lines.replace(lnbr + 2, "Driver = " + libdir + "/libtdsodbc.so");
lines.replace(lnbr + 3, "Setup = " + libdir + "/libtdsodbc.so");
QString text;
for(int j = 0; j < lines.count(); j++)
{
text.append(lines[j] + "\n");
}
odbcinst.open(QIODevice::WriteOnly | QIODevice::Text);
QTextStream updatefile(&odbcinst);
updatefile << text;
odbcinst.close();
}
}
#endif
This code creates the .odbcinst.ini file in your home directory if it doesn't exist and adds an entry for FreeTDS. If it does exist, it will append to the end of the file. If an entry for FreeTDS exists in the file already, it will update the existing file. Here's a guide for setting up FreeTDS if you haven't already: http://pzuk.wordpress.com/2012/02/03/how-to-make-freetds-unixodbc-and-qt-working-together/
Note, that the code for configuring FreeTDS that I posted is only required if you want to bundle FreeTDS with your application and have the libary path setup correctly from where you launch. It runs as a standard user and not as root so everything is done in the local user account.

How to get a list video capture devices NAMES (web cameras) using Qt (crossplatform)? (C++)

So all I need is simple - a list of currently avaliable video capture devices (web cameras). I need it in simple C++ Qt console app. By list I mean something like such console output:
1) Asus Web Camera
2) Sony Web Camera
So my question is how to cout such list using Qt C++? (if it is possible I'd love to see how to do it in pure Qt - no extra libs...)
also from this series:
How to get a list of video capture devices on linux? and special details on getting cameras NAMES with correct, tested answers
How to get a list of video capture devices on Mac OS? with correct, not yet tested by my answers
How to get a list of video capture devices on windows? with correct, tested answers
How to get a list video capture devices NAMES using Qt (crossplatform)?
I used this example code to list the cameras and get some info about them.
#include <QtMultimedia/QCameraInfo>
QList<QCameraInfo> cameras = QCameraInfo::availableCameras();
foreach (const QCameraInfo &cameraInfo, cameras) {
qDebug() << "Name: " << cameraInfo.deviceName();
qDebug() << "Position: " << cameraInfo.position();
qDebug() << "Orientation: " << cameraInfo.orientation();
}
remember to include in pro file:
QT += multimedia
I've wrote the following code to list all the USB capture devices. Remember to include webcam.h and libwebcam.h and link your code to libwecam using -lwebcam.
bool QextCamera::listAvailableDevices(QStringList * captureDeviceList){
CResult ret;
CDevice *devices = NULL;
quint32 req_size = 0;
quint32 buffer_size = 0;
quint32 count = 0;
QStringList availableDevices;
c_init();
do {
if (devices){
free(devices);
}
if(req_size){
devices = (CDevice *)malloc(req_size);
if(devices == NULL){
// LOG ERROR...
return false;
}
buffer_size = req_size;
}
// Try to enumerate. If the buffer is not large enough, the required size is returned.
ret = c_enum_devices(devices, &req_size, &count);
if(ret != C_SUCCESS && ret != C_BUFFER_TOO_SMALL){
// LOG ERROR...
return false;
}
} while(buffer_size < req_size);
if(count == 0) {
// LOG ERROR...
return false;
}
for(quint32 i = 0; i < count; i++) {
CDevice *device = &devices[i];
availableDevices << QString("%1 : %2 : %3").arg(device->shortName).arg(device->driver).arg(device->location);
}
if(devices){
free(devices);
}
c_cleanup();
*captureDeviceList = availableDevices;
return true;
}