Skip to content

Commit

Permalink
Use uiLanguages preferences (#132)
Browse files Browse the repository at this point in the history
IB-7564

Signed-off-by: Raul Metsma <[email protected]>
  • Loading branch information
metsma authored Jun 21, 2023
1 parent 33d878c commit 2842d66
Show file tree
Hide file tree
Showing 7 changed files with 76 additions and 133 deletions.
3 changes: 2 additions & 1 deletion .github/workflows/build.yml
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ jobs:
runs-on: macos-latest
env:
MACOSX_DEPLOYMENT_TARGET: 10.15
HOMEBREW_NO_INSTALLED_DEPENDENTS_CHECK: 1
steps:
- name: Checkout
uses: actions/checkout@v3
Expand Down Expand Up @@ -61,7 +62,7 @@ jobs:
- name: Install Qt
uses: jurplel/install-qt-action@v2
with:
version: 6.4.1
version: 6.4.2
arch: win64_msvc2019_64
- name: Build
run: |
Expand Down
26 changes: 7 additions & 19 deletions Common.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,6 @@
#include <QtCore/QDir>
#include <QtCore/QFileInfo>
#include <QtCore/QOperatingSystemVersion>
#include <QtCore/QSettings>
#include <QtGui/QIcon>
#include <QtNetwork/QNetworkProxyFactory>

Expand All @@ -48,7 +47,9 @@ Common::Common( int &argc, char **argv, const QString &app, const QString &icon
Q_INIT_RESOURCE(common_tr);
#if defined(Q_OS_WIN)
AllowSetForegroundWindow( ASFW_ANY );
#ifdef NDEBUG
setLibraryPaths({ applicationDirPath() });
#endif
#elif defined(Q_OS_MAC)
qputenv("OPENSSL_CONF", applicationDirPath().toUtf8() + "../Resources/openssl.cnf");
#ifdef NDEBUG
Expand All @@ -66,7 +67,7 @@ QString Common::applicationOs()
{
#if defined(Q_OS_MAC)
const auto version = QOperatingSystemVersion::current();
return QStringLiteral("%1 %2.%3.%4 (%5/%6)")
return QLatin1String("%1 %2.%3.%4 (%5/%6)")
.arg(version.name())
.arg(version.majorVersion())
.arg(version.minorVersion())
Expand All @@ -77,7 +78,7 @@ QString Common::applicationOs()
QString product = QSysInfo::productType();
product[0] = product[0].toUpper();
QString version = QSysInfo::productVersion();
version.replace(QStringLiteral("server"), QStringLiteral("Server "));
version.replace(QLatin1String("server"), QLatin1String("Server "));
return QStringLiteral("%1 %2 %3 (%4/%5)")
.arg(product)
.arg(version)
Expand Down Expand Up @@ -106,27 +107,14 @@ void Common::msgHandler(QtMsgType type, const QMessageLogContext &ctx, const QSt
case QtFatalMsg: f.write("F"); break;
default: f.write("I"); break;
}
f.write(QStringLiteral(" %1 ").arg(ctx.category).toUtf8());
f.write(QStringLiteral(" %1 ").arg(QLatin1String(ctx.category)).toUtf8());
if(ctx.line > 0)
{
f.write(QStringLiteral("%1:%2 \"%3\" ")
.arg(QFileInfo(ctx.file).fileName())
.arg(QFileInfo(QString::fromLatin1(ctx.file)).fileName())
.arg(ctx.line)
.arg(ctx.function).toUtf8());
.arg(QLatin1String(ctx.function)).toUtf8());
}
f.write(msg.toUtf8());
f.write("\n");
}

QString Common::language()
{
QString deflang;
switch( QLocale().language() )
{
case QLocale::Russian: deflang = QStringLiteral("ru"); break;
case QLocale::Estonian: deflang = QStringLiteral("et"); break;
case QLocale::English:
default: deflang = QStringLiteral("en"); break;
}
return QSettings().value(QStringLiteral("Language"), deflang).toString();
}
2 changes: 0 additions & 2 deletions Common.h
Original file line number Diff line number Diff line change
Expand Up @@ -40,8 +40,6 @@ class Common: public BaseApplication
#endif

static QString applicationOs();
static void setAccessibleName( QLabel *widget );
static QString language();

private:
static void msgHandler(QtMsgType type, const QMessageLogContext &ctx, const QString &msg);
Expand Down
49 changes: 22 additions & 27 deletions Configuration.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -52,8 +52,7 @@ static QJsonObject toObject(const QByteArray &data) {
}

static QByteArray readFile(const QString &file) {
QFile f(file);
if(f.open(QFile::ReadOnly))
if(QFile f(file); f.open(QFile::ReadOnly))
return f.readAll();
qWarning() << "Failed to read file" << file;
return {};
Expand Down Expand Up @@ -83,8 +82,8 @@ class Configuration::Private
void Configuration::Private::initCache(bool clear)
{
#ifndef NO_CACHE
auto readAll = [clear, this](const QString &fileName, const QString &copy) {
QFile f(cache + fileName);
auto readAll = [clear, this](const QUrl &url, const QString &copy) {
QFile f(cache + url.fileName());
if(clear && f.exists())
f.remove();
if(!f.exists())
Expand All @@ -94,8 +93,8 @@ void Configuration::Private::initCache(bool clear)
}
return f.open(QFile::ReadOnly) ? f.readAll() : QByteArray();
};
setData(readAll(url.fileName(), QStringLiteral(":/config.json")),
readAll(rsaurl.fileName(), QStringLiteral(":/config.rsa")));
setData(readAll(url, QStringLiteral(":/config.json")),
readAll(rsaurl, QStringLiteral(":/config.rsa")));
#else
setData(readFile(QStringLiteral(":/config.json")),
readFile(QStringLiteral(":/config.rsa")));
Expand All @@ -107,25 +106,23 @@ void Configuration::Private::setData(const QByteArray &_data, const QByteArray &
data = _data;
signature = _signature;
dataobject = toObject(data);
#ifdef Q_OS_MAC
QSettings s2(QSettings::SystemScope, nullptr);
#if QT_VERSION >= QT_VERSION_CHECK(5, 13, 0)
QSettings system(QSettings::SystemScope);
#else
QSettings s2(QSettings::SystemScope, QApplication::organizationName(), QApplication::applicationName());
QSettings system(QSettings::SystemScope, QCoreApplication::organizationName(), QCoreApplication::applicationName());
#endif

for(const QString &key: s2.childKeys())
for(const QString &key: system.childKeys())
{
if(dataobject.contains(key))
if(!dataobject.contains(key))
continue;
QVariant value = system.value(key);
switch(value.type())
{
QVariant value = s2.value(key);
switch(value.type())
{
case QVariant::String:
dataobject[key] = QJsonValue(value.toString()); break;
case QVariant::StringList:
dataobject[key] = QJsonValue(QJsonArray::fromStringList(value.toStringList())); break;
default: break;
}
case QVariant::String:
dataobject[key] = QJsonValue(value.toString()); break;
case QVariant::StringList:
dataobject[key] = QJsonValue(QJsonArray::fromStringList(value.toStringList())); break;
default: break;
}
}
}
Expand Down Expand Up @@ -179,7 +176,7 @@ Configuration::Configuration(QObject *parent)
QFileInfo(d->url.fileName()).baseName());
d->req.setRawHeader("User-Agent", QStringLiteral("%1/%2 (%3) Lang: %4 Devices: %5")
.arg(QApplication::applicationName(), QApplication::applicationVersion(),
Common::applicationOs(), Common::language(), QPCSC::instance().drivers().join('/')).toUtf8());
Common::applicationOs(), QLocale().uiLanguages().first(), QPCSC::instance().drivers().join('/')).toUtf8());
#if QT_VERSION >= QT_VERSION_CHECK(5, 15, 0)
d->req.setTransferTimeout();
#endif
Expand Down Expand Up @@ -298,11 +295,9 @@ Configuration::Configuration(QObject *parent)
d->s.setValue(QStringLiteral("LastCheck"), QDate::currentDate().toString(QStringLiteral("yyyyMMdd")));
update();
}
// Scheduled update
else if(lastCheck < QDate::currentDate().addDays(-LAST_CHECK_DAYS))
update();
// DigiDoc4 updated
else if(QVersionNumber::fromString(QSettings().value(QStringLiteral("LastVersion")).toString()) <
// Scheduled update or DigiDoc4 updated
else if(lastCheck < QDate::currentDate().addDays(-LAST_CHECK_DAYS) ||
QVersionNumber::fromString(QSettings().value(QStringLiteral("LastVersion")).toString()) <
QVersionNumber::fromString(QApplication::applicationVersion()))
update();
#endif
Expand Down
107 changes: 39 additions & 68 deletions QPCSC.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ Q_LOGGING_CATEGORY(SCard,"QPCSC.SCard")
static QStringList stateToString(DWORD state)
{
QStringList result;
#define STATE(X) if(state & SCARD_STATE_##X) result << QStringLiteral(#X)
#define STATE(X) if(state & SCARD_STATE_##X) result.append(QStringLiteral(#X))
STATE(IGNORE);
STATE(CHANGED);
STATE(UNKNOWN);
Expand All @@ -69,28 +69,13 @@ LONG SCCall( const char *file, int line, const char *function, Func func, Args..
}
#define SC(API, ...) SCCall(__FILE__, __LINE__, "SCard"#API, SCard##API, __VA_ARGS__)

QByteArray QPCSCReader::Private::attrib( DWORD id ) const
{
if(!card)
return {};
DWORD size = 0;
LONG err = SC(GetAttrib, card, id, nullptr, &size);
if( err != SCARD_S_SUCCESS || !size )
return {};
QByteArray data(int(size), 0);
err = SC(GetAttrib, card, id, LPBYTE(data.data()), &size);
if( err != SCARD_S_SUCCESS || !size )
return {};
return data;
}

QHash<DRIVER_FEATURES,quint32> QPCSCReader::Private::features()
{
if(!featuresList.isEmpty())
return featuresList;
DWORD size = 0;
std::array<BYTE,256> feature{};
if(SC(Control, card, DWORD(CM_IOCTL_GET_FEATURE_REQUEST), nullptr, 0U, feature.data(), feature.size(), &size))
if(SC(Control, card, DWORD(CM_IOCTL_GET_FEATURE_REQUEST), nullptr, 0U, feature.data(), DWORD(feature.size()), &size))
return featuresList;
for(auto p = feature.cbegin(); std::distance(feature.cbegin(), p) < size; )
{
Expand Down Expand Up @@ -218,9 +203,9 @@ void QPCSC::run()
if(std::none_of(list.cbegin(), list.cend(), [&name](const SCARD_READERSTATE &state) { return strcmp(state.szReader, name) == 0; }))
list.push_back({ strdup(name), nullptr, 0, 0, 0, {} });
}
if(SC(GetStatusChange, pcsc.d->context, 5*1000, list.data(), DWORD(list.size())) != SCARD_S_SUCCESS)
if(SC(GetStatusChange, pcsc.d->context, 5*1000U, list.data(), DWORD(list.size())) != SCARD_S_SUCCESS)
continue;
for(std::vector<SCARD_READERSTATE>::iterator i = list.begin(); i != list.end(); )
for(auto i = list.begin(); i != list.end(); )
{
if((i->dwEventState & SCARD_STATE_CHANGED) == 0)
{
Expand Down Expand Up @@ -312,16 +297,6 @@ bool QPCSCReader::endTransaction( Reset reset )
return result;
}

QString QPCSCReader::friendlyName() const
{
return QString::fromLocal8Bit( d->attrib( SCARD_ATTR_DEVICE_FRIENDLY_NAME_A ) );
}

bool QPCSCReader::isConnected() const
{
return d->card;
}

bool QPCSCReader::isPinPad() const
{
if(d->reader.contains("HID Global OMNIKEY 3x21 Smart Card Reader") ||
Expand Down Expand Up @@ -350,7 +325,7 @@ QHash<QPCSCReader::Properties, int> QPCSCReader::properties() const
{
DWORD size = 0;
std::array<BYTE,256> recv{};
if(SC(Control, d->card, ioctl, nullptr, 0U, recv.data(), recv.size(), &size))
if(SC(Control, d->card, ioctl, nullptr, 0U, recv.data(), DWORD(recv.size()), &size))
return properties;
for(auto p = recv.cbegin(); std::distance(recv.cbegin(), p) < size; )
{
Expand Down Expand Up @@ -385,7 +360,7 @@ QStringList QPCSCReader::state() const
QPCSCReader::Result QPCSCReader::transfer( const QByteArray &apdu ) const
{
QByteArray data( 1024, 0 );
DWORD size = DWORD(data.size());
auto size = DWORD(data.size());

qCDebug(APDU).nospace() << 'T' << d->io.dwProtocol - 1 << "> " << apdu.toHex().constData();
LONG ret = SC(Transmit, d->card, &d->io,
Expand Down Expand Up @@ -431,53 +406,49 @@ QPCSCReader::Result QPCSCReader::transferCTL(const QByteArray &apdu, bool verify
}

quint8 PINFrameOffset = 0, PINLengthOffset = 0;
#define SET() \
data->bTimerOut = 30; \
data->bTimerOut2 = 30; \
data->bmFormatString = FormatASCII|AlignLeft|quint8(PINFrameOffset << 4)|PINFrameOffsetUnitBits; \
data->bmPINBlockString = PINLengthNone << 5|PINFrameSizeAuto; \
data->bmPINLengthFormat = PINLengthOffsetUnitBits|PINLengthOffset; \
data->wPINMaxExtraDigit = quint16(minlen << 8) | 12; \
data->bEntryValidationCondition = ValidOnKeyPressed; \
data->wLangId = lang; \
data->bTeoPrologue[0] = 0x00; \
data->bTeoPrologue[1] = 0x00; \
data->bTeoPrologue[2] = 0x00; \
data->ulDataLength = quint32(apdu.size())

QByteArray cmd( 255, 0 );
auto toByteArray = [&](auto &data) {
data.bTimerOut = 30;
data.bTimerOut2 = 30;
data.bmFormatString = FormatASCII|AlignLeft|quint8(PINFrameOffset << 4)|PINFrameOffsetUnitBits;
data.bmPINBlockString = PINLengthNone << 5|PINFrameSizeAuto;
data.bmPINLengthFormat = PINLengthOffsetUnitBits|PINLengthOffset;
data.wPINMaxExtraDigit = quint16(minlen << 8) | 12;
data.bEntryValidationCondition = ValidOnKeyPressed;
data.wLangId = lang;
data.ulDataLength = quint32(apdu.size());
return QByteArray((const char*)&data, sizeof(data) - 1) + apdu;
};

QByteArray cmd;
if( verify )
{
PIN_VERIFY_STRUCTURE *data = (PIN_VERIFY_STRUCTURE*)cmd.data();
SET();
data->bNumberMessage = display ? CCIDDefaultInvitationMessage : NoInvitationMessage;
data->bMsgIndex = NoInvitationMessage;
cmd.resize( sizeof(PIN_VERIFY_STRUCTURE) - 1 );
PIN_VERIFY_STRUCTURE data{};
data.bNumberMessage = display ? CCIDDefaultInvitationMessage : NoInvitationMessage;
data.bMsgIndex = NoInvitationMessage;
cmd = toByteArray(data);
}
else
{
PIN_MODIFY_STRUCTURE *data = (PIN_MODIFY_STRUCTURE*)cmd.data();
SET();
data->bNumberMessage = display ? ThreeInvitationMessage : NoInvitationMessage;
data->bInsertionOffsetOld = 0x00;
data->bInsertionOffsetNew = newPINOffset;
data->bConfirmPIN = ConfirmNewPin;
PIN_MODIFY_STRUCTURE data{};
data.bNumberMessage = display ? ThreeInvitationMessage : NoInvitationMessage;
data.bInsertionOffsetOld = 0x00;
data.bInsertionOffsetNew = newPINOffset;
data.bConfirmPIN = ConfirmNewPin;
if(requestCurrentPIN)
{
data->bConfirmPIN |= RequestCurrentPin;
data->bMsgIndex1 = NoInvitationMessage;
data->bMsgIndex2 = OneInvitationMessage;
data->bMsgIndex3 = TwoInvitationMessage;
data.bConfirmPIN |= RequestCurrentPin;
data.bMsgIndex1 = NoInvitationMessage;
data.bMsgIndex2 = OneInvitationMessage;
data.bMsgIndex3 = TwoInvitationMessage;
}
else
{
data->bMsgIndex1 = OneInvitationMessage;
data->bMsgIndex2 = TwoInvitationMessage;
data->bMsgIndex3 = ThreeInvitationMessage;
data.bMsgIndex1 = OneInvitationMessage;
data.bMsgIndex2 = TwoInvitationMessage;
data.bMsgIndex3 = ThreeInvitationMessage;
}
cmd.resize( sizeof(PIN_MODIFY_STRUCTURE) - 1 );
cmd = toByteArray(data);
}
cmd += apdu;

DWORD ioctl = features.value( verify ? FEATURE_VERIFY_PIN_START : FEATURE_MODIFY_PIN_START );
if( !ioctl )
Expand All @@ -486,7 +457,7 @@ QPCSCReader::Result QPCSCReader::transferCTL(const QByteArray &apdu, bool verify
qCDebug(APDU).nospace() << 'T' << d->io.dwProtocol - 1 << "> " << apdu.toHex().constData();
qCDebug(APDU).nospace() << "CTL" << "> " << cmd.toHex().constData();
QByteArray data( 255 + 3, 0 );
DWORD size = DWORD(data.size());
auto size = DWORD(data.size());
LONG err = SC(Control, d->card, ioctl, cmd.constData(), DWORD(cmd.size()), LPVOID(data.data()), DWORD(data.size()), &size);

if( DWORD finish = features.value( verify ? FEATURE_VERIFY_PIN_FINISH : FEATURE_MODIFY_PIN_FINISH ) )
Expand All @@ -495,7 +466,7 @@ QPCSCReader::Result QPCSCReader::transferCTL(const QByteArray &apdu, bool verify
err = SC(Control, d->card, finish, nullptr, 0U, LPVOID(data.data()), DWORD(data.size()), &size);
}

Result result = { data.mid(int(size - 2), 2), data.left(int(size - 2)), quint32(err) };
Result result { data.mid(int(size - 2), 2), data.left(int(size - 2)), quint32(err) };
qCDebug(APDU).nospace() << 'T' << d->io.dwProtocol - 1 << "< " << result.SW.toHex().constData();
if(!result.data.isEmpty()) qCDebug(APDU).nospace() << data.left(int(size)).toHex().constData();
return result;
Expand Down
2 changes: 0 additions & 2 deletions QPCSC.h
Original file line number Diff line number Diff line change
Expand Up @@ -106,8 +106,6 @@ class QPCSCReader final: public QObject
~QPCSCReader() final;

QByteArray atr() const;
QString friendlyName() const;
bool isConnected() const;
bool isPinPad() const;
bool isPresent() const;
QString name() const;
Expand Down
Loading

0 comments on commit 2842d66

Please sign in to comment.