File indexing completed on 2024-04-21 16:32:41

0001 /*
0002     SPDX-FileCopyrightText: 2001 Shie Erlich <krusader@users.sourceforge.net>
0003     SPDX-FileCopyrightText: 2001 Rafi Yanai <krusader@users.sourceforge.net>
0004     SPDX-FileCopyrightText: 2004-2022 Krusader Krew <https://krusader.org>
0005 
0006     SPDX-License-Identifier: GPL-2.0-or-later
0007 */
0008 
0009 #include "kr7zencryptionchecker.h"
0010 
0011 Kr7zEncryptionChecker::Kr7zEncryptionChecker()
0012     : encrypted(false)
0013     , lastData()
0014 {
0015     setOutputChannelMode(KProcess::SeparateChannels); // without this output redirection has no effect!
0016     connect(this, &Kr7zEncryptionChecker::readyReadStandardOutput, this, [=]() {
0017         receivedOutput();
0018     });
0019 }
0020 
0021 void Kr7zEncryptionChecker::setupChildProcess()
0022 {
0023     // This function is called after the fork but for the exec. We create a process group
0024     // to work around a broken wrapper script of 7z. Without this only the wrapper is killed.
0025     setsid(); // make this process leader of a new process group
0026 }
0027 
0028 void Kr7zEncryptionChecker::receivedOutput()
0029 {
0030     // Reminder: If that function is modified, it's important to research if the
0031     // changes must also be applied to `kio_krarcProtocol::check7zOutputForPassword()`
0032 
0033     QString data = QString::fromLocal8Bit(this->readAllStandardOutput());
0034 
0035     QString checkable = lastData + data;
0036 
0037     QStringList lines = checkable.split('\n');
0038     lastData = lines[lines.count() - 1];
0039     for (int i = 0; i != lines.count(); i++) {
0040         QString line = lines[i].trimmed().toLower();
0041         int ndx = line.indexOf("listing"); // Reminder: Lower-case letters are used
0042         if (ndx >= 0)
0043             line.truncate(ndx);
0044         if (line.isEmpty())
0045             continue;
0046 
0047         if ((line.contains("password") && line.contains("enter")) || line == QStringLiteral("encrypted = +")) {
0048             encrypted = true;
0049             ::kill(static_cast<pid_t>(-processId()), SIGKILL); // kill the whole process group by giving the negative PID
0050             break;
0051         }
0052     }
0053 }
0054 
0055 bool Kr7zEncryptionChecker::isEncrypted()
0056 {
0057     return encrypted;
0058 }