Bug 1791130 - Speed up s/mime recipient certificate check. r=mkmelin

Differential Revision: https://phabricator.services.mozilla.com/D162199

--HG--
extra : amend_source : 4b5ab18edb826469bfe81a0f581dbcf2acfae861
This commit is contained in:
Kai Engert 2022-11-18 21:31:54 +11:00
Родитель 99af105385
Коммит a66a5e6f08
3 изменённых файлов: 100 добавлений и 22 удалений

Просмотреть файл

@ -172,6 +172,8 @@ var gBodyFromArgs;
// gSMFields separate allows switching as needed.
var gSMFields = null;
var gSMCertsMap = new Map();
var gSelectedTechnologyIsPGP = false;
// The initial flags store the value we used at composer open time.
@ -3457,36 +3459,35 @@ async function checkRecipientKeys() {
].createInstance(Ci.nsISMimeJSHelper);
let outEmailAddresses = {};
let outCertIssuedInfos = {};
let outCertExpiresInfos = {};
let outCerts = {};
let outCanEncrypt = {};
helper.getRecipientCertsInfo(
compFields,
outEmailAddresses,
outCertIssuedInfos,
outCertExpiresInfos,
outCerts,
outCanEncrypt
);
helper.getRecipients(compFields, outEmailAddresses);
let checks = [];
for (let i = 0; i < outEmailAddresses.value.length; i++) {
if (!outCerts.value[i]) {
emailsWithMissingCerts.push(outEmailAddresses.value[i]);
let email = outEmailAddresses.value[i];
let certFromCache = gSMCertsMap.get(email);
if (certFromCache) {
continue;
}
checks.push(
verifyCertUsable(outCerts.value[i])
.then(usage => {})
.catch(error => {
emailsWithMissingCerts.push(outEmailAddresses.value[i]);
})
let outCertIssuedInfo = {};
let outCertExpiresInfo = {};
let outCert = {};
helper.getValidCertInfo(
email,
outCertIssuedInfo,
outCertExpiresInfo,
outCert
);
if (outCert.value) {
gSMCertsMap.set(email, outCert.value);
} else {
emailsWithMissingCerts.push(email);
continue;
}
}
await Promise.all(checks);
if (!emailsWithMissingCerts.length) {
haveAllCerts = true;

Просмотреть файл

@ -19,6 +19,7 @@ interface nsISMimeJSHelper : nsISupports
/**
* Obtains detailed information about the certificate availability
* status of email recipients.
* The returned certificates have NOT been checked for validity yet
*
* @param compFields - Attributes of the composed message.
* @param emailAddresses - The list of all recipient email addresses
@ -34,6 +35,17 @@ interface nsISMimeJSHelper : nsISupports
out Array<nsIX509Cert> certs,
out boolean canEncrypt);
void getRecipients(in nsIMsgCompFields compFields,
out Array<AString> emailAddresses);
/**
* Only a VALID certificate will be returned.
*/
void getValidCertInfo(in AString email,
out AString certIssuedInfo,
out AString certExpiresInfo,
out nsIX509Cert cert);
/**
* Obtains a list of email addresses where valid email recipient certificates
* are not yet available.

Просмотреть файл

@ -40,6 +40,70 @@ static void PRTimeToLocalDateString(PRTime time, nsAString& result) {
style, &explodedTime, result);
}
NS_IMETHODIMP nsSMimeJSHelper::GetRecipients(
nsIMsgCompFields* compFields, nsTArray<nsString>& emailAddresses) {
nsTArray<nsCString> mailboxes;
nsresult rv = getMailboxList(compFields, mailboxes);
NS_ENSURE_SUCCESS(rv, rv);
uint32_t mailbox_count = mailboxes.Length();
emailAddresses.ClearAndRetainStorage();
emailAddresses.SetCapacity(mailbox_count);
rv = NS_OK;
for (uint32_t i = 0; i < mailbox_count; ++i) {
const nsCString& email = mailboxes[i];
nsCString email_lowercase;
ToLowerCase(email, email_lowercase);
emailAddresses.AppendElement(NS_ConvertUTF8toUTF16(email));
}
return NS_OK;
}
NS_IMETHODIMP nsSMimeJSHelper::GetValidCertInfo(const nsAString& email,
nsAString& certIssuedInfo,
nsAString& certExpiresInfo,
nsIX509Cert** cert) {
nsCOMPtr<nsIX509CertDB> certdb = do_GetService(NS_X509CERTDB_CONTRACTID);
*cert = nullptr;
nsresult rv = NS_OK;
nsCOMPtr<nsIMsgComposeSecure> composeSecure =
do_CreateInstance("@mozilla.org/messengercompose/composesecure;1", &rv);
NS_ENSURE_SUCCESS(rv, rv);
NS_ConvertUTF16toUTF8 emailC(email);
nsCString email_lowercase;
ToLowerCase(emailC, email_lowercase);
// Find only valid certificate.
if (NS_SUCCEEDED(
composeSecure->FindCertByEmailAddress(email_lowercase, true, cert))) {
nsCOMPtr<nsIX509CertValidity> validity;
rv = (*cert)->GetValidity(getter_AddRefs(validity));
if (NS_SUCCEEDED(rv)) {
PRTime notBefore;
rv = validity->GetNotBefore(&notBefore);
if (NS_SUCCEEDED(rv)) {
PRTimeToLocalDateString(notBefore, certIssuedInfo);
}
PRTime notAfter;
rv = validity->GetNotAfter(&notAfter);
if (NS_SUCCEEDED(rv)) {
PRTimeToLocalDateString(notAfter, certExpiresInfo);
}
}
}
return NS_OK;
}
NS_IMETHODIMP nsSMimeJSHelper::GetRecipientCertsInfo(
nsIMsgCompFields* compFields, nsTArray<nsString>& emailAddresses,
nsTArray<nsString>& certIssuedInfos, nsTArray<nsString>& certExpiresInfos,
@ -79,6 +143,7 @@ NS_IMETHODIMP nsSMimeJSHelper::GetRecipientCertsInfo(
nsCString email_lowercase;
ToLowerCase(email, email_lowercase);
// Find certificate regardless of validity.
if (NS_SUCCEEDED(composeSecure->FindCertByEmailAddress(
email_lowercase, false, getter_AddRefs(cert)))) {
nsCOMPtr<nsIX509CertValidity> validity;