mirror of
https://bitbucket.org/smil3y/kde-playground.git
synced 2025-02-23 18:32:51 +00:00
347 lines
8.2 KiB
C++
347 lines
8.2 KiB
C++
/*
|
|
* convertscanfiles.cpp
|
|
*
|
|
* Copyright (C) 2008-2011 Christoph Pfister <christophpfister@gmail.com>
|
|
*
|
|
* This program is free software; you can redistribute it and/or modify
|
|
* it under the terms of the GNU General Public License as published by
|
|
* the Free Software Foundation; either version 2 of the License, or
|
|
* (at your option) any later version.
|
|
*
|
|
* This program is distributed in the hope that it will be useful,
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
* GNU General Public License for more details.
|
|
*
|
|
* You should have received a copy of the GNU General Public License along
|
|
* with this program; if not, write to the Free Software Foundation, Inc.,
|
|
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
|
*/
|
|
|
|
#include <QCoreApplication>
|
|
#include <QDate>
|
|
#include <QDebug>
|
|
#include <QDir>
|
|
#include "../src/dvb/dvbtransponder.h"
|
|
|
|
class NumericalLessThan
|
|
{
|
|
public:
|
|
bool operator()(const QString &x, const QString &y)
|
|
{
|
|
int i = 0;
|
|
|
|
while (true) {
|
|
if ((i == x.length()) || (i == y.length())) {
|
|
return x.length() < y.length();
|
|
}
|
|
|
|
if (x.at(i) != y.at(i)) {
|
|
break;
|
|
}
|
|
|
|
++i;
|
|
}
|
|
|
|
int xIndex = x.indexOf(' ', i);
|
|
|
|
if (xIndex == -1) {
|
|
xIndex = x.length();
|
|
}
|
|
|
|
int yIndex = y.indexOf(' ', i);
|
|
|
|
if (yIndex == -1) {
|
|
yIndex = y.length();
|
|
}
|
|
|
|
if (xIndex != yIndex) {
|
|
return xIndex < yIndex;
|
|
} else {
|
|
return x.at(i) < y.at(i);
|
|
}
|
|
}
|
|
};
|
|
|
|
static QString parseLine(DvbTransponderBase::TransmissionType type, const QString &line, const QString &fileName)
|
|
{
|
|
switch (type) {
|
|
case DvbTransponderBase::Invalid:
|
|
break;
|
|
case DvbTransponderBase::DvbC: {
|
|
DvbCTransponder transponder;
|
|
|
|
if (!transponder.fromString(line)) {
|
|
break;
|
|
}
|
|
|
|
if (transponder.modulation == DvbCTransponder::ModulationAuto) {
|
|
qWarning() << "Warning: modulation == AUTO in file" << fileName;
|
|
}
|
|
|
|
if (transponder.fecRate != DvbCTransponder::FecNone) {
|
|
qWarning() << "Warning: fec rate != NONE in file" << fileName;
|
|
}
|
|
|
|
return transponder.toString();
|
|
}
|
|
case DvbTransponderBase::DvbS: {
|
|
if (line.startsWith(QLatin1String("S "))) {
|
|
DvbSTransponder transponder;
|
|
|
|
if (!transponder.fromString(line)) {
|
|
break;
|
|
}
|
|
|
|
if (transponder.fecRate == DvbSTransponder::FecNone) {
|
|
qWarning() << "Warning: fec rate == NONE in file" << fileName;
|
|
}
|
|
|
|
// fecRate == AUTO is ok
|
|
|
|
return transponder.toString();
|
|
} else {
|
|
DvbS2Transponder transponder;
|
|
|
|
if (!transponder.fromString(line)) {
|
|
break;
|
|
}
|
|
|
|
if (transponder.fecRate == DvbSTransponder::FecNone) {
|
|
qWarning() << "Warning: fec rate == NONE in file" << fileName;
|
|
}
|
|
|
|
// fecRate == AUTO is ok
|
|
|
|
return transponder.toString();
|
|
}
|
|
}
|
|
case DvbTransponderBase::DvbS2:
|
|
break;
|
|
case DvbTransponderBase::DvbT: {
|
|
DvbTTransponder transponder;
|
|
|
|
if (!transponder.fromString(line)) {
|
|
break;
|
|
}
|
|
|
|
if (transponder.bandwidth == DvbTTransponder::BandwidthAuto) {
|
|
qWarning() << "Warning: bandwidth == AUTO in file" << fileName;
|
|
}
|
|
|
|
if ((transponder.modulation == DvbTTransponder::ModulationAuto) && !fileName.startsWith(QLatin1String("auto-"))) {
|
|
qWarning() << "Warning: modulation == AUTO in file" << fileName;
|
|
}
|
|
|
|
if (transponder.fecRateHigh == DvbTTransponder::FecNone) {
|
|
qWarning() << "Warning: fec rate high == NONE in file" << fileName;
|
|
}
|
|
|
|
// fecRateHigh == AUTO is ok
|
|
|
|
if (transponder.fecRateLow != DvbTTransponder::FecNone) {
|
|
qWarning() << "Warning: fec rate low != NONE in file" << fileName;
|
|
}
|
|
|
|
if ((transponder.transmissionMode == DvbTTransponder::TransmissionModeAuto) && !fileName.startsWith(QLatin1String("auto-"))) {
|
|
qWarning() << "Warning: transmission mode == AUTO in file" << fileName;
|
|
}
|
|
|
|
if ((transponder.guardInterval == DvbTTransponder::GuardIntervalAuto) && !fileName.startsWith(QLatin1String("auto-"))) {
|
|
qWarning() << "Warning: guard interval == AUTO in file" << fileName;
|
|
}
|
|
|
|
if (transponder.hierarchy != DvbTTransponder::HierarchyNone) {
|
|
qWarning() << "Warning: hierarchy != NONE in file" << fileName;
|
|
}
|
|
|
|
return transponder.toString();
|
|
}
|
|
case DvbTransponderBase::Atsc: {
|
|
AtscTransponder transponder;
|
|
|
|
if (!transponder.fromString(line)) {
|
|
break;
|
|
}
|
|
|
|
if (transponder.modulation == AtscTransponder::ModulationAuto) {
|
|
qWarning() << "Warning: modulation == AUTO in file" << fileName;
|
|
}
|
|
|
|
return transponder.toString();
|
|
}
|
|
}
|
|
|
|
return QString();
|
|
}
|
|
|
|
static void readScanDirectory(QTextStream &out, const QString &path, DvbTransponderBase::TransmissionType type)
|
|
{
|
|
QDir dir;
|
|
|
|
switch (type) {
|
|
case DvbTransponderBase::Invalid:
|
|
break;
|
|
case DvbTransponderBase::DvbC:
|
|
dir.setPath(path + "/dvb-c");
|
|
break;
|
|
case DvbTransponderBase::DvbS:
|
|
dir.setPath(path + "/dvb-s");
|
|
break;
|
|
case DvbTransponderBase::DvbS2:
|
|
break;
|
|
case DvbTransponderBase::DvbT:
|
|
dir.setPath(path + "/dvb-t");
|
|
break;
|
|
case DvbTransponderBase::Atsc:
|
|
dir.setPath(path + "/atsc");
|
|
break;
|
|
}
|
|
|
|
if (!dir.exists()) {
|
|
qCritical() << "Error: can't open directory" << dir.path();
|
|
return;
|
|
}
|
|
|
|
foreach (const QString &fileName, dir.entryList(QDir::Files, QDir::Name)) {
|
|
QFile file(dir.filePath(fileName));
|
|
|
|
if (!file.open(QIODevice::ReadOnly)) {
|
|
qCritical() << "Error: can't open file" << file.fileName();
|
|
return;
|
|
}
|
|
|
|
QTextStream stream(&file);
|
|
stream.setCodec("UTF-8");
|
|
QList<QString> transponders;
|
|
|
|
while (!stream.atEnd()) {
|
|
QString line = stream.readLine();
|
|
|
|
int pos = line.indexOf('#');
|
|
|
|
if (pos != -1) {
|
|
while ((pos > 0) && (line[pos - 1] == ' ')) {
|
|
--pos;
|
|
}
|
|
|
|
line.truncate(pos);
|
|
}
|
|
|
|
if (line.isEmpty()) {
|
|
continue;
|
|
}
|
|
|
|
QString string = parseLine(type, line, fileName);
|
|
|
|
if (string.isEmpty()) {
|
|
qCritical() << "Error: can't parse line" << line << "in file" << fileName;
|
|
return;
|
|
}
|
|
|
|
// reduce multiple spaces to one space and remove leading zeros
|
|
|
|
for (int i = 1; i < line.length(); ++i) {
|
|
if (line.at(i - 1) != ' ') {
|
|
continue;
|
|
}
|
|
|
|
if ((line.at(i) == ' ') || (line.at(i) == '0')) {
|
|
line.remove(i, 1);
|
|
--i;
|
|
}
|
|
}
|
|
|
|
if (line != string) {
|
|
qWarning() << "Warning: suboptimal representation" << line << "<-->" << string << "in file" << fileName;
|
|
}
|
|
|
|
transponders.append(string);
|
|
}
|
|
|
|
if (transponders.isEmpty()) {
|
|
qWarning() << "Warning: no transponder found in file" << fileName;
|
|
continue;
|
|
}
|
|
|
|
QString name = dir.dirName() + '/' + fileName;
|
|
|
|
if (type == DvbSTransponder::DvbS) {
|
|
// use upper case for orbital position
|
|
name[name.size() - 1] = name.at(name.size() - 1).toUpper();
|
|
|
|
QString source = name;
|
|
source.remove(0, source.lastIndexOf('-') + 1);
|
|
|
|
bool ok = false;
|
|
|
|
if (source.endsWith('E')) {
|
|
source.chop(1);
|
|
source.toDouble(&ok);
|
|
} else if (source.endsWith('W')) {
|
|
source.chop(1);
|
|
source.toDouble(&ok);
|
|
}
|
|
|
|
if (!ok) {
|
|
qWarning() << "Warning: invalid orbital position for file" << fileName;
|
|
}
|
|
}
|
|
|
|
out << '[' << name << "]\n";
|
|
|
|
qSort(transponders.begin(), transponders.end(), NumericalLessThan());
|
|
|
|
foreach (const QString &transponder, transponders) {
|
|
out << transponder << '\n';
|
|
}
|
|
}
|
|
}
|
|
|
|
int main(int argc, char *argv[])
|
|
{
|
|
// QCoreApplication is needed for proper file name handling
|
|
QCoreApplication app(argc, argv);
|
|
|
|
if (argc != 3) {
|
|
qCritical() << "Syntax: convertscanfiles <scan file dir> <output file>";
|
|
return 1;
|
|
}
|
|
|
|
QByteArray data;
|
|
QTextStream out(&data);
|
|
out.setCodec("UTF-8");
|
|
|
|
out << "# this file is automatically generated from http://linuxtv.org/hg/dvb-apps\n";
|
|
out << "[date]\n";
|
|
out << QDate::currentDate().toString(Qt::ISODate) << '\n';
|
|
|
|
QString path(argv[1]);
|
|
|
|
readScanDirectory(out, path, DvbTransponderBase::DvbC);
|
|
readScanDirectory(out, path, DvbTransponderBase::DvbS);
|
|
readScanDirectory(out, path, DvbTransponderBase::DvbT);
|
|
readScanDirectory(out, path, DvbTransponderBase::Atsc);
|
|
|
|
out.flush();
|
|
|
|
QFile file(argv[2]);
|
|
|
|
if (!file.open(QIODevice::WriteOnly | QIODevice::Truncate)) {
|
|
qCritical() << "Error: can't open file" << file.fileName();
|
|
return 1;
|
|
}
|
|
|
|
file.write(data);
|
|
|
|
QFile compressedFile(QString(argv[2]) + ".qz");
|
|
|
|
if (!compressedFile.open(QIODevice::WriteOnly | QIODevice::Truncate)) {
|
|
qCritical() << "Error: can't open file" << compressedFile.fileName();
|
|
return 1;
|
|
}
|
|
|
|
compressedFile.write(qCompress(data, 9));
|
|
|
|
return 0;
|
|
}
|