File indexing completed on 2025-03-16 08:32:46
0001 /* 0002 SPDX-FileCopyrightText: 2006, 2007 Jimmy Gilles <jimmygilles@gmail.com> 0003 SPDX-FileCopyrightText: 2007, 2008, 2009, 2010, 2012, 2013, 2014, 2017 Rolf Eike Beer <kde@opensource.sf-tec.de> 0004 SPDX-License-Identifier: GPL-2.0-or-later 0005 */ 0006 0007 #include "kgpgkey.h" 0008 0009 #include "convert.h" 0010 0011 0012 namespace KgpgCore 0013 { 0014 0015 static QString _describe_key_strength(KgpgKeyAlgo algorithm, const uint size, const QString &curve) 0016 { 0017 if (!curve.isEmpty()) 0018 return curve; 0019 0020 QString prefix; 0021 0022 switch(algorithm) 0023 { 0024 case ALGO_RSA: prefix = QStringLiteral("rsa"); break; 0025 case ALGO_ELGAMAL: prefix = QStringLiteral("elg"); break; 0026 case ALGO_DSA: prefix = QStringLiteral("dsa"); break; 0027 } 0028 0029 return prefix + QString::number(size); 0030 } 0031 0032 //BEGIN KeySub 0033 KgpgKeySubPrivate::KgpgKeySubPrivate(const QString &id, const uint size, const KgpgKeyTrust trust, const KgpgKeyAlgo algo, 0034 const KgpgSubKeyType type, const QDateTime &date, const QString &curve) 0035 : gpgsubvalid(false), 0036 gpgsubid(id), 0037 gpgsubsize(size), 0038 gpgsubcreation(date), 0039 gpgsubtrust(trust), 0040 gpgsubalgo(algo), 0041 gpgsubtype(type), 0042 gpgcurve(curve) 0043 { 0044 } 0045 0046 bool KgpgKeySubPrivate::operator==(const KgpgKeySubPrivate &other) const 0047 { 0048 if (gpgsubvalid != other.gpgsubvalid) return false; 0049 if (gpgsubalgo != other.gpgsubalgo) return false; 0050 if (gpgsubid != other.gpgsubid) return false; 0051 if (gpgsubsize != other.gpgsubsize) return false; 0052 if (gpgsubexpiration != other.gpgsubexpiration) return false; 0053 if (gpgsubcreation != other.gpgsubcreation) return false; 0054 if (gpgsubtrust != other.gpgsubtrust) return false; 0055 if (gpgsubtype != other.gpgsubtype) return false; 0056 return true; 0057 } 0058 0059 KgpgKeySub::KgpgKeySub(const QString &id, const uint size, const KgpgKeyTrust trust, const KgpgKeyAlgo algo, const KgpgSubKeyType type, 0060 const QDateTime &date, const QString &curve) 0061 : d(new KgpgKeySubPrivate(id, size, trust, algo, type, date, curve)) 0062 { 0063 } 0064 0065 KgpgKeySub::KgpgKeySub(const KgpgKeySub &other) 0066 : d(other.d) 0067 { 0068 } 0069 0070 void KgpgKeySub::setExpiration(const QDateTime &date) 0071 { 0072 d->gpgsubexpiration = date; 0073 } 0074 0075 void KgpgKeySub::setValid(const bool valid) 0076 { 0077 d->gpgsubvalid = valid; 0078 } 0079 0080 QString KgpgKeySub::id() const 0081 { 0082 return d->gpgsubid; 0083 } 0084 0085 uint KgpgKeySub::size() const 0086 { 0087 return d->gpgsubsize; 0088 } 0089 0090 QString KgpgKeySub::strength() const 0091 { 0092 return _describe_key_strength(algorithm(), size(), d->gpgcurve); 0093 } 0094 0095 bool KgpgKeySub::unlimited() const 0096 { 0097 return d->gpgsubexpiration.isNull(); 0098 } 0099 0100 QDateTime KgpgKeySub::expirationDate() const 0101 { 0102 return d->gpgsubexpiration; 0103 } 0104 0105 QDateTime KgpgKeySub::creationDate() const 0106 { 0107 return d->gpgsubcreation; 0108 } 0109 0110 KgpgKeyTrust KgpgKeySub::trust() const 0111 { 0112 return d->gpgsubtrust; 0113 } 0114 0115 KgpgKeyAlgo KgpgKeySub::algorithm() const 0116 { 0117 return d->gpgsubalgo; 0118 } 0119 0120 bool KgpgKeySub::valid() const 0121 { 0122 return d->gpgsubvalid; 0123 } 0124 0125 KgpgSubKeyType KgpgKeySub::type() const 0126 { 0127 return d->gpgsubtype; 0128 } 0129 0130 QString KgpgKeySub::curve() const 0131 { 0132 return d->gpgcurve; 0133 } 0134 0135 bool KgpgKeySub::operator==(const KgpgKeySub &other) const 0136 { 0137 if (d == other.d) return true; 0138 if ((*d) == (*(other.d))) return true; 0139 return false; 0140 } 0141 0142 KgpgKeySub& KgpgKeySub::operator=(const KgpgKeySub &other) 0143 { 0144 d = other.d; 0145 return *this; 0146 } 0147 0148 //END KeySub 0149 0150 0151 //BEGIN Key 0152 0153 KgpgKeyPrivate::KgpgKeyPrivate(const QString &id, const uint size, const KgpgKeyTrust trust, const KgpgKeyAlgo algo, const KgpgSubKeyType subtype, 0154 const KgpgSubKeyType keytype, const QDateTime &creationDate, const QString &curve) 0155 : gpgkeysecret(false), 0156 gpgkeyvalid(false), 0157 gpgkeyid(id), 0158 gpgkeysize(size), 0159 gpgkeytrust(trust), 0160 gpgkeycreation(creationDate), 0161 gpgkeyalgo(algo), 0162 gpgsubtype(subtype), 0163 gpgkeytype(keytype), 0164 gpgcurve(curve), 0165 gpgsublist(new KgpgKeySubList()) 0166 { 0167 } 0168 0169 bool KgpgKeyPrivate::operator==(const KgpgKeyPrivate &other) const 0170 { 0171 if (gpgkeysecret != other.gpgkeysecret) return false; 0172 if (gpgkeyvalid != other.gpgkeyvalid) return false; 0173 if (gpgkeymail != other.gpgkeymail) return false; 0174 if (gpgkeyname != other.gpgkeyname) return false; 0175 if (gpgkeycomment != other.gpgkeycomment) return false; 0176 if (gpgkeyfingerprint != other.gpgkeyfingerprint) return false; 0177 if (gpgkeyid != other.gpgkeyid) return false; 0178 if (gpgkeysize != other.gpgkeysize) return false; 0179 if (gpgkeyownertrust != other.gpgkeyownertrust) return false; 0180 if (gpgkeytrust != other.gpgkeytrust) return false; 0181 if (gpgkeycreation != other.gpgkeycreation) return false; 0182 if (gpgkeyexpiration != other.gpgkeyexpiration) return false; 0183 if (gpgkeyalgo != other.gpgkeyalgo) return false; 0184 if (gpgsubtype != other.gpgsubtype) return false; 0185 if (gpgkeytype != other.gpgkeytype) return false; 0186 if (gpgsublist != other.gpgsublist) return false; 0187 return true; 0188 } 0189 0190 KgpgKey::KgpgKey(const QString &id, const uint size, const KgpgKeyTrust trust, const KgpgKeyAlgo algo, const KgpgSubKeyType subtype, 0191 const KgpgSubKeyType keytype, const QDateTime &creationDate, const QString &curve) 0192 : d(new KgpgKeyPrivate(id, size, trust, algo, subtype, keytype, creationDate, curve)) 0193 { 0194 } 0195 0196 KgpgKey::KgpgKey(const KgpgKey &other) 0197 : d(other.d) 0198 { 0199 } 0200 0201 void KgpgKey::setSecret(const bool secret) 0202 { 0203 d->gpgkeysecret = secret; 0204 } 0205 0206 void KgpgKey::setValid(const bool valid) 0207 { 0208 d->gpgkeyvalid = valid; 0209 } 0210 0211 void KgpgKey::setName(const QString &name) 0212 { 0213 d->gpgkeyname = name; 0214 } 0215 0216 void KgpgKey::setEmail(const QString &email) 0217 { 0218 d->gpgkeymail = email; 0219 } 0220 0221 void KgpgKey::setComment(const QString &comment) 0222 { 0223 d->gpgkeycomment = comment; 0224 } 0225 0226 void KgpgKey::setFingerprint(const QString &fingerprint) 0227 { 0228 d->gpgkeyfingerprint = fingerprint; 0229 } 0230 0231 void KgpgKey::setOwnerTrust(const gpgme_validity_t owtrust) 0232 { 0233 d->gpgkeyownertrust = owtrust; 0234 } 0235 0236 void KgpgKey::setExpiration(const QDateTime &date) 0237 { 0238 d->gpgkeyexpiration = date; 0239 } 0240 0241 bool KgpgKey::secret() const 0242 { 0243 return d->gpgkeysecret; 0244 } 0245 0246 bool KgpgKey::valid() const 0247 { 0248 return d->gpgkeyvalid; 0249 } 0250 0251 QString KgpgKey::id() const 0252 { 0253 return d->gpgkeyid.right(8); 0254 } 0255 0256 QString KgpgKey::fullId() const 0257 { 0258 return d->gpgkeyid; 0259 } 0260 0261 QString KgpgKey::name() const 0262 { 0263 return d->gpgkeyname; 0264 } 0265 0266 QString KgpgKey::email() const 0267 { 0268 return d->gpgkeymail; 0269 } 0270 0271 QString KgpgKey::comment() const 0272 { 0273 return d->gpgkeycomment; 0274 } 0275 0276 const QString &KgpgKey::fingerprint() const 0277 { 0278 return d->gpgkeyfingerprint; 0279 } 0280 0281 uint KgpgKey::size() const 0282 { 0283 return d->gpgkeysize; 0284 } 0285 0286 QString KgpgKey::strength() const 0287 { 0288 return _describe_key_strength(algorithm(), size(), d->gpgcurve); 0289 } 0290 0291 /** 0292 * @brief find the "best" encryption key 0293 * 0294 * The "best" is the first one that is not expired, or simply the 0295 * first one. 0296 */ 0297 static const KgpgKeySub * 0298 bestEncryptionKey(const KgpgKeySubList &list) 0299 { 0300 const KgpgKeySub *enc = nullptr; 0301 // Get the first encryption subkey 0302 for (const KgpgKeySub &k : list) { 0303 if (k.type() & SKT_ENCRYPTION) { 0304 // if the first encryption subkey is expired 0305 // check if there is one that is not 0306 if (k.trust() > TRUST_EXPIRED) 0307 return &k; 0308 if (enc == nullptr) 0309 enc = &k; 0310 } 0311 } 0312 0313 return enc; 0314 } 0315 0316 uint KgpgKey::encryptionSize() const 0317 { 0318 const KgpgKeySub *enc = bestEncryptionKey(*d->gpgsublist); 0319 if (enc != nullptr) 0320 return enc->size(); 0321 return 0; 0322 } 0323 0324 QString KgpgKey::encryptionStrength() const 0325 { 0326 const KgpgKeySub *enc = bestEncryptionKey(*d->gpgsublist); 0327 if (enc != nullptr) 0328 return _describe_key_strength(enc->algorithm(), enc->size(), enc->curve()); 0329 return QString(); 0330 } 0331 0332 gpgme_validity_t KgpgKey::ownerTrust() const 0333 { 0334 return d->gpgkeyownertrust; 0335 } 0336 0337 KgpgKeyTrust KgpgKey::trust() const 0338 { 0339 return d->gpgkeytrust; 0340 } 0341 0342 QDateTime KgpgKey::creationDate() const 0343 { 0344 return d->gpgkeycreation; 0345 } 0346 0347 QDateTime KgpgKey::expirationDate() const 0348 { 0349 return d->gpgkeyexpiration; 0350 } 0351 0352 bool KgpgKey::unlimited() const 0353 { 0354 return d->gpgkeyexpiration.isNull(); 0355 } 0356 0357 KgpgKeyAlgo KgpgKey::algorithm() const 0358 { 0359 return d->gpgkeyalgo; 0360 } 0361 0362 KgpgKeyAlgo KgpgKey::encryptionAlgorithm() const 0363 { 0364 // Get the first encryption subkey 0365 auto it = std::find_if(d->gpgsublist->cbegin(), d->gpgsublist->cend(), 0366 [](const KgpgKeySub &k) { return k.type() & SKT_ENCRYPTION; }); 0367 if (it != d->gpgsublist->cend()) 0368 return it->algorithm(); 0369 0370 return ALGO_UNKNOWN; 0371 } 0372 0373 KgpgSubKeyType KgpgKey::subtype() const 0374 { 0375 return d->gpgsubtype; 0376 } 0377 0378 KgpgSubKeyType KgpgKey::keytype() const 0379 { 0380 return d->gpgkeytype; 0381 } 0382 0383 QString KgpgKey::curve() const 0384 { 0385 return d->gpgcurve; 0386 } 0387 0388 KgpgKeySubListPtr KgpgKey::subList() const 0389 { 0390 return d->gpgsublist; 0391 } 0392 0393 bool KgpgKey::operator==(const KgpgKey &other) const 0394 { 0395 if (d == other.d) return true; 0396 if ((*d) == (*(other.d))) return true; 0397 return false; 0398 } 0399 0400 KgpgKey& KgpgKey::operator=(const KgpgKey &other) 0401 { 0402 d = other.d; 0403 return *this; 0404 } 0405 0406 KgpgKeyList::operator QStringList() const 0407 { 0408 QStringList res; 0409 res.reserve(count()); 0410 0411 for (const KgpgKey &key : *this) 0412 res << key.fullId(); 0413 0414 return res; 0415 } 0416 0417 //END Key 0418 0419 } // namespace KgpgCore