Add Kyber to algorithm strings.
[qpwmc.git] / pwmdKeyGenDialog.cpp
blobb80ba06c4799e3ffe09e6d122b7feedf45ae36e1
1 /*
2 Copyright (C) 2017-2024 Ben Kibbey <bjk@luxsci.net>
4 This file is part of qpwmc.
6 This library is free software; you can redistribute it and/or
7 modify it under the terms of the GNU Lesser General Public
8 License as published by the Free Software Foundation; either
9 version 2.1 of the License, or (at your option) any later version.
11 This library is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 Lesser General Public License for more details.
16 You should have received a copy of the GNU Lesser General Public
17 License along with this library; if not, write to the Free Software
18 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301
19 USA
21 #include <QPushButton>
22 #include <QCommonStyle>
23 #include "cmdIds.h"
24 #include "pwmdKeyGenDialog.h"
25 #include "pwmdFileDialog.h"
27 static time_t now;
29 PwmdKeyGenDialog::PwmdKeyGenDialog (QWidget *p, Pwmd *h) : QDialog (p)
31 pwm = h;
32 genKeyError = 0;
33 //setWindowFlags (Qt::WindowTitleHint);
34 ui.setupUi (this);
35 ui.f_generate->setHidden (true);
36 QSize s = size ();
37 resize (s.rwidth(), 0);
39 disconnect(ui.buttonBox, SIGNAL(accepted ()), this, SLOT(accept ()));
40 QPushButton *pb = ui.buttonBox->button (QDialogButtonBox::Ok);
41 pb->disconnect (this);
42 connect (pb, SIGNAL (clicked ()), this, SLOT (slotGenerate ()));
43 connect (ui.ck_neverExpire, SIGNAL (stateChanged (int)), this,
44 SLOT (slotNeverExpire (int)));
45 connect (ui.ck_protected, SIGNAL (clicked ()), this, SLOT (slotProtected ()));
46 connect (ui.le_name, SIGNAL (textChanged (const QString &)), this,
47 SLOT (slotNameChanged (const QString &)));
48 connect (ui.le_email, SIGNAL (textChanged (const QString &)), this,
49 SLOT (slotEmailChanged (const QString &)));
50 connect (ui.le_subKey, SIGNAL (textChanged (const QString &)), this,
51 SLOT (slotSubKeyChanged (const QString &)));
52 connect (ui.tb_keyFile, SIGNAL (clicked ()), this, SLOT (slotSelectKeyFile ()));
53 QCommonStyle style;
54 ui.tb_keyFile->setIcon (QIcon (":icons/rodentia-icons_folder-open-blue.svg"));
55 connect (pwm, SIGNAL (commandResult (PwmdCommandQueueItem *, QString, gpg_error_t, bool)), this, SLOT (slotCommandResult (PwmdCommandQueueItem *, QString, gpg_error_t, bool)));
57 QDateTime dt;
58 now = time (nullptr);
59 dt.setSecsSinceEpoch (now);
60 ui.de_expire->setDateTime (dt.addYears (3));
61 ui.de_expire->setMinimumDateTime (dt);
63 QString user = qgetenv ("USER");
64 ui.le_name->setText (qgetenv ("REALNAME").size () ? qgetenv ("REALNAME") : user);
65 ui.le_email->setText (qgetenv ("EMAIL").size () ? qgetenv ("EMAIL") : user);
68 PwmdKeyGenDialog::~PwmdKeyGenDialog ()
72 void
73 PwmdKeyGenDialog::slotCommandResult (PwmdCommandQueueItem *item,
74 QString result, gpg_error_t rc,
75 bool queued)
77 (void)result;
79 if ((item->id () >= 0 && item->id () <= PwmdCmdIdOpenMax)
80 || item->id () >= PwmdCmdIdSaveMax)
82 item->setSeen ();
83 return;
86 if (rc && !item->checkError (rc) && !queued)
88 genKeyError = rc;
89 Pwmd::showError (rc, pwm);
92 item->setSeen ();
95 void
96 PwmdKeyGenDialog::slotNameChanged (const QString &s)
98 QPushButton *pb = ui.buttonBox->button (QDialogButtonBox::Ok);
99 pb->setEnabled (!(s.isEmpty () && ui.le_email->text ().isEmpty ()));
102 void
103 PwmdKeyGenDialog::slotEmailChanged (const QString &s)
105 QPushButton *pb = ui.buttonBox->button (QDialogButtonBox::Ok);
106 pb->setEnabled (!(s.isEmpty () && ui.le_name->text ().isEmpty ()));
109 void
110 PwmdKeyGenDialog::slotSubKeyChanged (const QString &s)
112 bool b = s.isEmpty ();
114 ui.le_name->setEnabled (b);
115 ui.le_email->setEnabled (b);
118 void
119 PwmdKeyGenDialog::slotProtected ()
121 ui.le_keyFile->setEnabled (ui.ck_protected->isChecked ());
122 ui.tb_keyFile->setEnabled (ui.ck_protected->isChecked ());
125 void
126 PwmdKeyGenDialog::slotNeverExpire (int s)
128 ui.de_expire->setEnabled (!(s == Qt::Checked));
131 QString
132 PwmdKeyGenDialog::name ()
134 return ui.le_name->text ();
137 void
138 PwmdKeyGenDialog::setName (const QString &s)
140 ui.le_name->setText (s);
144 QString
145 PwmdKeyGenDialog::email ()
147 return ui.le_email->text ();
150 void
151 PwmdKeyGenDialog::setEmail (const QString &s)
153 ui.le_email->setText (s);
156 QString
157 PwmdKeyGenDialog::algorithm ()
159 if (ui.le_algorithm->text ().isEmpty ())
160 return "default";
162 return ui.le_algorithm->text ();
165 bool
166 PwmdKeyGenDialog::protection ()
168 return ui.ck_protected->isChecked ();
171 unsigned long
172 PwmdKeyGenDialog::expires ()
174 unsigned long t;
176 if (ui.ck_neverExpire->isChecked ())
177 return 0;
179 t = ui.de_expire->dateTime ().toSecsSinceEpoch () - now;
180 if (!t)
181 return (unsigned long)time (nullptr) - ui.de_expire->dateTime ().toSecsSinceEpoch ();
183 return t;
186 QString
187 PwmdKeyGenDialog::usage ()
189 if (ui.rb_sign->isChecked ())
190 return "sign";
191 else if (ui.rb_encrypt->isChecked ())
192 return "encrypt";
194 return "default";
197 void
198 PwmdKeyGenDialog::setSubKey (PwmdKey *key)
200 setName (key->userIds ().at (0)->name ());
201 setEmail (key->userIds ().at (0)->email ());
202 ui.le_subKey->setText (key->subKeys ().at (0)->fingerprint ());
205 QString
206 PwmdKeyGenDialog::subKey ()
208 return ui.le_subKey->text ();
211 void
212 PwmdKeyGenDialog::slotGenerate ()
214 QString args;
215 PwmdInquireData *inq = nullptr;
217 if (!name ().isEmpty ())
219 args += "--userid=\"" + name ();
220 if (!email ().isEmpty ())
221 args += " <" + email () + ">";
222 args += "\"";
224 else if (!email ().isEmpty ())
225 args += "--userid=\"" + email () + "\"";
227 if (!algorithm ().isEmpty ())
228 args += " --algo=" + algorithm ();
230 args += " --usage=" + usage ();
232 if (ui.ck_protected->isEnabled () && !protection ())
233 args += " --no-passphrase";
235 if (ui.ck_neverExpire->isChecked ())
236 args += QString (" --no-expire");
237 else
238 args += QString (" --expire=%1").arg (expires ());
240 if (!subKey().isEmpty ())
241 args += QString (" --subkey-of=%1").arg (subKey ());
243 pwmd_socket_t type;
244 pwmd_socket_type (pwm->handle (), &type);
245 if (type != PWMD_SOCKET_LOCAL || !ui.le_keyFile->text ().isEmpty ())
247 gpg_error_t rc;
249 inq = new PwmdInquireData (pwm->handle (), pwm->filename ());
250 if (!ui.le_keyFile->text ().isEmpty ())
252 inq->setKeyFile (ui.le_keyFile->text ());
253 inq->setEncryptKeyFile (ui.le_keyFile->text ());
254 inq->setSignKeyFile (ui.le_keyFile->text ());
257 rc = pwmd_setopt (pwm->handle (), PWMD_OPTION_LOCAL_PINENTRY, 1);
258 if (!rc)
259 rc = pwmd_setopt (pwm->handle (), PWMD_OPTION_OVERRIDE_INQUIRE, 1);
261 if (rc)
263 delete inq;
264 pwm->showError (rc, pwm);
265 return;
269 QSize origSize = size ();
270 ui.f_params->setEnabled (false);
271 ui.f_generate->setHidden (false);
272 ui.buttonBox->setEnabled (false);
274 genKeyError = 0;
275 PwmdCommandQueueItem *item = nullptr;
276 if (pwm->genkey (args, inq ? Pwmd::inquireCallback : 0, inq, false, &item))
278 while (pwm->isQueued (item))
280 QApplication::processEvents ();
281 QThread::msleep (50);
285 if (genKeyError)
287 ui.f_params->setEnabled (true);
288 ui.f_generate->setHidden (true);
289 ui.buttonBox->setEnabled (true);
290 QApplication::processEvents ();
291 resize (origSize);
292 return;
295 QDialog::accept ();
298 void
299 PwmdKeyGenDialog::slotSelectKeyFile ()
301 PwmdFileDialog d (this, tr ("Passphrase file"));
303 d.setFileMode (PwmdFileDialog::ExistingFile);
304 d.setOption (PwmdFileDialog::ReadOnly);
305 #ifdef Q_OS_ANDROID
306 d.setWindowState (Qt::WindowFullScreen);
307 #endif
309 if (!d.exec () || !d.selectedFiles ().count ())
310 return;
311 ui.le_keyFile->setText (d.selectedFiles ().at (0));