diff -Nur filezilla.orig/src/interface/verifycertdialog.cpp filezilla/src/interface/verifycertdialog.cpp
old
|
new
|
|
147 | 147 | XRCCTRL(*m_pDlg, "ID_ALWAYS", wxCheckBox)->Hide(); |
148 | 148 | } |
149 | 149 | |
| 150 | m_curSelect = 0; |
150 | 151 | m_certificates = notification.GetCertificates(); |
151 | 152 | if (m_certificates.size() == 1) { |
152 | 153 | XRCCTRL(*m_pDlg, "ID_CHAIN_DESC", wxStaticText)->Hide(); |
… |
… |
|
230 | 231 | m_pDlg = 0; |
231 | 232 | } |
232 | 233 | |
| 234 | wxString CVerifyCertDialog::GetCNValue(const wxString& dn) |
| 235 | { |
| 236 | wxStringTokenizer tokens(dn, _T(",")); |
| 237 | |
| 238 | std::list<wxString> tokenlist; |
| 239 | while (tokens.HasMoreTokens()) |
| 240 | tokenlist.push_back(tokens.GetNextToken()); |
| 241 | |
| 242 | wxString prefix = _T("CN="); |
| 243 | int len = prefix.Length(); |
| 244 | |
| 245 | wxString value; |
| 246 | |
| 247 | bool append = false; |
| 248 | |
| 249 | auto iter = tokenlist.begin(); |
| 250 | while (iter != tokenlist.end()) |
| 251 | { |
| 252 | if (!append) |
| 253 | { |
| 254 | if (iter->Left(len) != prefix) |
| 255 | { |
| 256 | ++iter; |
| 257 | continue; |
| 258 | } |
| 259 | if (!value.empty()) |
| 260 | value += _T("\n"); |
| 261 | } |
| 262 | else |
| 263 | { |
| 264 | append = false; |
| 265 | value += _T(","); |
| 266 | } |
| 267 | value += iter->Mid(len); |
| 268 | if (iter->Last() == '\\') |
| 269 | { |
| 270 | value.RemoveLast(); |
| 271 | append = true; |
| 272 | len = 0; |
| 273 | } |
| 274 | auto remove = iter++; |
| 275 | tokenlist.erase(remove); |
| 276 | } |
| 277 | return value; |
| 278 | } |
| 279 | |
233 | 280 | void CVerifyCertDialog::ParseDN(wxWindow* parent, const wxString& dn, wxSizer* pSizer) |
234 | 281 | { |
235 | 282 | pSizer->Clear(true); |
… |
… |
|
329 | 376 | |
330 | 377 | LoadTrustedCerts(); |
331 | 378 | |
332 | | unsigned int len; |
333 | | CCertificate cert = notification.GetCertificates()[0]; |
334 | | const unsigned char* data = cert.GetRawData(len); |
| 379 | for (unsigned int i = 0; i < notification.GetCertificates().size(); ++i) { |
| 380 | if (i > 0) { |
| 381 | unsigned int len; |
| 382 | CCertificate cert = notification.GetCertificates()[i]; |
| 383 | const unsigned char* data = cert.GetRawData(len); |
| 384 | wxString sCN = GetCNValue(cert.GetSubject()); |
335 | 385 | |
336 | | return IsTrusted(notification.GetHost(), notification.GetPort(), data, len, false); |
| 386 | if (IsTrusted(sCN, 0, data, len, false)) { |
| 387 | return true; |
| 388 | } |
| 389 | } |
| 390 | else { |
| 391 | unsigned int len; |
| 392 | CCertificate cert = notification.GetCertificates()[0]; |
| 393 | const unsigned char* data = cert.GetRawData(len); |
| 394 | |
| 395 | if (IsTrusted(notification.GetHost(), notification.GetPort(), data, len, false)) { |
| 396 | return true; |
| 397 | } |
| 398 | } |
| 399 | } |
| 400 | return false; |
337 | 401 | } |
338 | 402 | |
339 | 403 | bool CVerifyCertDialog::DoIsTrusted(const wxString& host, int port, const unsigned char* data, unsigned int len, std::list<CVerifyCertDialog::t_certData> const& trustedCerts) |
… |
… |
|
465 | 529 | |
466 | 530 | data.host = GetTextElement(cert, "Host"); |
467 | 531 | data.port = GetTextElementInt(cert, "Port"); |
468 | | if (data.host.empty() || data.port < 1 || data.port > 65535) |
| 532 | if (data.port == 0) { |
| 533 | // use for non-first cert |
| 534 | } |
| 535 | else if (data.host.empty() || data.port < 1 || data.port > 65535) |
469 | 536 | remove = cert; |
470 | 537 | |
471 | 538 | int64_t activationTime = GetTextElementInt(cert, "ActivationTime", 0); |
… |
… |
|
498 | 565 | |
499 | 566 | void CVerifyCertDialog::SetPermanentlyTrusted(CCertificateNotification const& notification) |
500 | 567 | { |
501 | | const CCertificate certificate = notification.GetCertificates()[0]; |
| 568 | wxString sCN = _T(""); |
| 569 | const CCertificate certificate = notification.GetCertificates()[m_curSelect]; |
502 | 570 | unsigned int len; |
503 | 571 | const unsigned char* const data = certificate.GetRawData(len); |
504 | 572 | |
505 | 573 | CReentrantInterProcessMutexLocker mutex(MUTEX_TRUSTEDCERTS); |
506 | 574 | LoadTrustedCerts(); |
507 | 575 | |
508 | | if (IsTrusted(notification.GetHost(), notification.GetPort(), data, len, true)) { |
509 | | return; |
| 576 | if (m_curSelect > 0) { |
| 577 | sCN = GetCNValue(certificate.GetSubject()); |
| 578 | if (IsTrusted(sCN, 0, data, len, true)) { |
| 579 | return; |
| 580 | } |
| 581 | } |
| 582 | else { |
| 583 | if (IsTrusted(notification.GetHost(), notification.GetPort(), data, len, true)) { |
| 584 | return; |
| 585 | } |
510 | 586 | } |
511 | 587 | |
512 | 588 | t_certData cert; |
513 | | cert.host = notification.GetHost(); |
514 | | cert.port = notification.GetPort(); |
| 589 | if (m_curSelect > 0) { |
| 590 | cert.host = sCN; |
| 591 | cert.port = 0; |
| 592 | } |
| 593 | else { |
| 594 | cert.host = notification.GetHost(); |
| 595 | cert.port = notification.GetPort(); |
| 596 | } |
515 | 597 | cert.len = len; |
516 | 598 | cert.data = new unsigned char[len]; |
517 | 599 | memcpy(cert.data, data, len); |
… |
… |
|
534 | 616 | AddTextElement(xCert, "Data", ConvertHexToString(data, len)); |
535 | 617 | AddTextElement(xCert, "ActivationTime", static_cast<int64_t>(certificate.GetActivationTime().get_time_t())); |
536 | 618 | AddTextElement(xCert, "ExpirationTime", static_cast<int64_t>(certificate.GetExpirationTime().get_time_t())); |
537 | | AddTextElement(xCert, "Host", notification.GetHost()); |
538 | | AddTextElement(xCert, "Port", notification.GetPort()); |
| 619 | if (m_curSelect > 0) { |
| 620 | AddTextElement(xCert, "Host", sCN); |
| 621 | AddTextElement(xCert, "Port", 0); |
| 622 | } |
| 623 | else { |
| 624 | AddTextElement(xCert, "Host", notification.GetHost()); |
| 625 | AddTextElement(xCert, "Port", notification.GetPort()); |
| 626 | } |
539 | 627 | |
540 | 628 | m_xmlFile.Save(true); |
541 | 629 | } |
… |
… |
|
590 | 678 | int sel = event.GetSelection(); |
591 | 679 | if (sel < 0 || sel > (int)m_certificates.size()) |
592 | 680 | return; |
| 681 | m_curSelect = sel; |
593 | 682 | DisplayCert(m_pDlg, m_certificates[sel]); |
594 | 683 | |
595 | 684 | m_pDlg->Layout(); |
diff -Nur filezilla.orig/src/interface/verifycertdialog.h filezilla/src/interface/verifycertdialog.h
old
|
new
|
|
28 | 28 | |
29 | 29 | bool DisplayCert(wxDialogEx* pDlg, const CCertificate& cert); |
30 | 30 | |
| 31 | wxString GetCNValue(const wxString& dn); |
31 | 32 | void ParseDN(wxWindow* parent, const wxString& dn, wxSizer* pSizer); |
32 | 33 | void ParseDN_by_prefix(wxWindow* parent, std::list<wxString>& tokens, wxString prefix, const wxString& name, wxSizer* pSizer, bool decode = false); |
33 | 34 | |
… |
… |
|
50 | 51 | wxSizer* m_pSubjectSizer{}; |
51 | 52 | wxSizer* m_pIssuerSizer{}; |
52 | 53 | int line_height_{}; |
| 54 | unsigned int m_curSelect; |
53 | 55 | |
54 | 56 | void OnCertificateChoice(wxCommandEvent& event); |
55 | 57 | }; |