File indexing completed on 2024-05-05 04:38:47
0001 /* 0002 SPDX-FileCopyrightText: 2002 John Firebaugh <jfirebaugh@kde.org> 0003 SPDX-FileCopyrightText: 2007 Andreas Pakulat <apaku@gmx.de> 0004 SPDX-FileCopyrightText: 2007 Oswald Buddenhagen <ossi@kde.org> 0005 0006 SPDX-License-Identifier: LGPL-2.0-or-later 0007 */ 0008 0009 #include "processlinemaker.h" 0010 0011 #include <QProcess> 0012 #include <QStringList> 0013 0014 namespace KDevelop { 0015 0016 class ProcessLineMakerPrivate 0017 { 0018 public: 0019 QByteArray stdoutbuf; 0020 QByteArray stderrbuf; 0021 ProcessLineMaker* p; 0022 QProcess* m_proc; 0023 0024 explicit ProcessLineMakerPrivate(ProcessLineMaker* maker) 0025 : p(maker) 0026 { 0027 } 0028 0029 void slotReadyReadStdout() 0030 { 0031 stdoutbuf += m_proc->readAllStandardOutput(); 0032 processStdOut(); 0033 } 0034 0035 static QStringList streamToStrings(QByteArray& data) 0036 { 0037 QStringList lineList; 0038 int pos; 0039 while ((pos = data.indexOf('\n')) != -1) { 0040 if (pos > 0 && data.at(pos - 1) == '\r') 0041 lineList << QString::fromLocal8Bit(data.constData(), pos - 1); 0042 else 0043 lineList << QString::fromLocal8Bit(data.constData(), pos); 0044 data.remove(0, pos + 1); 0045 } 0046 return lineList; 0047 } 0048 0049 void processStdOut() 0050 { 0051 emit p->receivedStdoutLines(streamToStrings(stdoutbuf)); 0052 } 0053 0054 void slotReadyReadStderr() 0055 { 0056 stderrbuf += m_proc->readAllStandardError(); 0057 processStdErr(); 0058 } 0059 0060 void processStdErr() 0061 { 0062 emit p->receivedStderrLines(streamToStrings(stderrbuf)); 0063 } 0064 0065 }; 0066 0067 ProcessLineMaker::ProcessLineMaker(QObject* parent) 0068 : QObject(parent) 0069 , d_ptr(new ProcessLineMakerPrivate(this)) 0070 { 0071 } 0072 0073 ProcessLineMaker::ProcessLineMaker(QProcess* proc, QObject* parent) 0074 : QObject(parent) 0075 , d_ptr(new ProcessLineMakerPrivate(this)) 0076 { 0077 Q_D(ProcessLineMaker); 0078 0079 d->m_proc = proc; 0080 connect(proc, &QProcess::readyReadStandardOutput, 0081 this, [this] { 0082 Q_D(ProcessLineMaker); 0083 d->slotReadyReadStdout(); 0084 }); 0085 connect(proc, &QProcess::readyReadStandardError, 0086 this, [this] { 0087 Q_D(ProcessLineMaker); 0088 d->slotReadyReadStderr(); 0089 }); 0090 } 0091 0092 ProcessLineMaker::~ProcessLineMaker() = default; 0093 0094 void ProcessLineMaker::slotReceivedStdout(const QByteArray& buffer) 0095 { 0096 Q_D(ProcessLineMaker); 0097 0098 d->stdoutbuf += buffer; 0099 d->processStdOut(); 0100 } 0101 0102 void ProcessLineMaker::slotReceivedStderr(const QByteArray& buffer) 0103 { 0104 Q_D(ProcessLineMaker); 0105 0106 d->stderrbuf += buffer; 0107 d->processStdErr(); 0108 } 0109 0110 void ProcessLineMaker::discardBuffers() 0111 { 0112 Q_D(ProcessLineMaker); 0113 0114 d->stderrbuf.truncate(0); 0115 d->stdoutbuf.truncate(0); 0116 } 0117 0118 void ProcessLineMaker::flushBuffers() 0119 { 0120 Q_D(ProcessLineMaker); 0121 0122 if (!d->stdoutbuf.isEmpty()) 0123 emit receivedStdoutLines(QStringList(QString::fromLocal8Bit(d->stdoutbuf))); 0124 if (!d->stderrbuf.isEmpty()) 0125 emit receivedStderrLines(QStringList(QString::fromLocal8Bit(d->stderrbuf))); 0126 discardBuffers(); 0127 } 0128 0129 } 0130 0131 #include "moc_processlinemaker.cpp"