implement using the e-cert-trust foo. (e_cert_get_email): implement.

2003-11-12  Chris Toshok  <toshok@ximian.com>

	* lib/e-cert.c (e_cert_get_cert_type): implement using the
	e-cert-trust foo.
	(e_cert_get_email): implement.

	* lib/e-cert.h: add UNKNOWN cert type.

	* gui/smime-ui.glade: fix capitalization of "Import" on the
	contact certificate page.

	* gui/certificate-manager.c (import_contact): new function.
	implement email cert importing.
	(delete_contact): new function.
	(unload_certs): implement for E_CERT_CONTACT.
	(certificate_manager_config_control_new): get the contact cert
	action buttons from libglade.

	* lib/e-cert-db.c (handle_ca_cert_download): mostly implement the
	trust settings correctly.  this still needs work pending the CA
	trust dialog's completion.
	(e_cert_db_delete_cert): fix the ifdef'ed code.
	(e_cert_db_import_user_cert): remove the ifdef'ed body of this,
	since it was copied from the CA code.

	* lib/Makefile.am (libessmime_la_SOURCES): add e-cert-trust.[ch]

	* lib/e-cert-trust.[ch]: new files, basically c&p nsNSSCertTrust
	from mozilla's PSM.

svn path=/trunk/; revision=23308
This commit is contained in:
Chris Toshok
2003-11-13 02:23:52 +00:00
committed by Chris Toshok
parent 7e734202c2
commit bdba680ed5
9 changed files with 784 additions and 110 deletions

View File

@ -1,3 +1,33 @@
2003-11-12 Chris Toshok <toshok@ximian.com>
* lib/e-cert.c (e_cert_get_cert_type): implement using the
e-cert-trust foo.
(e_cert_get_email): implement.
* lib/e-cert.h: add UNKNOWN cert type.
* gui/smime-ui.glade: fix capitalization of "Import" on the
contact certificate page.
* gui/certificate-manager.c (import_contact): new function.
implement email cert importing.
(delete_contact): new function.
(unload_certs): implement for E_CERT_CONTACT.
(certificate_manager_config_control_new): get the contact cert
action buttons from libglade.
* lib/e-cert-db.c (handle_ca_cert_download): mostly implement the
trust settings correctly. this still needs work pending the CA
trust dialog's completion.
(e_cert_db_delete_cert): fix the ifdef'ed code.
(e_cert_db_import_user_cert): remove the ifdef'ed body of this,
since it was copied from the CA code.
* lib/Makefile.am (libessmime_la_SOURCES): add e-cert-trust.[ch]
* lib/e-cert-trust.[ch]: new files, basically c&p nsNSSCertTrust
from mozilla's PSM.
2003-11-11 Chris Toshok <toshok@ximian.com>
* tests/import-cert.c (main): don't init NSS here. it's done in

View File

@ -55,6 +55,10 @@ typedef struct {
GtkWidget *contactcerts_treeview;
GtkTreeStore *contactcerts_treemodel;
GHashTable *contactcerts_root_hash;
GtkWidget *view_contact_button;
GtkWidget *edit_contact_button;
GtkWidget *import_contact_button;
GtkWidget *delete_contact_button;
GtkWidget *authoritycerts_treeview;
GtkTreeStore *authoritycerts_treemodel;
@ -186,16 +190,79 @@ initialize_yourcerts_ui (CertificateManagerData *cfm)
}
}
static void
import_contact (GtkWidget *widget, CertificateManagerData *cfm)
{
GtkWidget *filesel = gtk_file_selection_new (_("Select a cert to import..."));
if (GTK_RESPONSE_OK == gtk_dialog_run (GTK_DIALOG (filesel))) {
const char *filename = gtk_file_selection_get_filename (GTK_FILE_SELECTION (filesel));
if (e_cert_db_import_certs_from_file (e_cert_db_peek (),
filename,
E_CERT_CONTACT,
NULL)) {
/* there's no telling how many certificates were added during the import,
so we blow away the contact cert display and regenerate it. */
unload_certs (cfm, E_CERT_CONTACT);
load_certs (cfm, E_CERT_CONTACT, add_contact_cert);
}
}
gtk_widget_destroy (filesel);
}
static void
delete_contact (GtkWidget *widget, CertificateManagerData *cfm)
{
GtkTreeIter iter;
if (gtk_tree_selection_get_selected (gtk_tree_view_get_selection (GTK_TREE_VIEW(cfm->contactcerts_treeview)),
NULL,
&iter)) {
ECert *cert;
gtk_tree_model_get (GTK_TREE_MODEL (cfm->contactcerts_treemodel),
&iter,
3, &cert,
-1);
if (cert) {
printf ("DELETE\n");
e_cert_db_delete_cert (e_cert_db_peek (), cert);
gtk_tree_store_remove (cfm->contactcerts_treemodel,
&iter);
/* we need two unrefs here, one to unref the
gtk_tree_model_get above, and one to unref
the initial ref when we created the cert
and added it to the tree */
g_object_unref (cert);
g_object_unref (cert);
}
}
}
static void
contactcerts_selection_changed (GtkTreeSelection *selection, CertificateManagerData *cfm)
{
#if 0
handle_selection_changed (gtk_tree_view_get_selection (GTK_TREE_VIEW(cfm->contactcerts_treeview)),
1 /* XXX */,
NULL,
NULL,
NULL);
#endif
3,
cfm->view_contact_button,
cfm->edit_contact_button,
cfm->delete_contact_button);
}
static GtkTreeStore*
create_contactcerts_treemodel (void)
{
return gtk_tree_store_new (4,
G_TYPE_STRING,
G_TYPE_STRING,
G_TYPE_STRING,
G_TYPE_OBJECT);
}
static void
@ -222,12 +289,6 @@ initialize_contactcerts_ui (CertificateManagerData *cfm)
"text", 2,
NULL));
cfm->contactcerts_treemodel = gtk_tree_store_new (3,
G_TYPE_STRING,
G_TYPE_STRING,
G_TYPE_STRING,
G_TYPE_OBJECT);
gtk_tree_view_set_model (GTK_TREE_VIEW (cfm->contactcerts_treeview),
GTK_TREE_MODEL (cfm->contactcerts_treemodel));
@ -235,6 +296,13 @@ initialize_contactcerts_ui (CertificateManagerData *cfm)
selection = gtk_tree_view_get_selection (GTK_TREE_VIEW (cfm->contactcerts_treeview));
g_signal_connect (selection, "changed", G_CALLBACK (contactcerts_selection_changed), cfm);
if (cfm->import_contact_button)
g_signal_connect (cfm->import_contact_button, "clicked", G_CALLBACK (import_contact), cfm);
if (cfm->delete_contact_button)
g_signal_connect (cfm->delete_contact_button, "clicked", G_CALLBACK (delete_contact), cfm);
}
static gint
@ -400,7 +468,40 @@ add_user_cert (CertificateManagerData *cfm, ECert *cert)
static void
add_contact_cert (CertificateManagerData *cfm, ECert *cert)
{
/* nothing yet */
GtkTreeIter iter;
GtkTreeIter *parent_iter = NULL;
const char *organization = e_cert_get_org (cert);
if (organization) {
parent_iter = g_hash_table_lookup (cfm->contactcerts_root_hash, organization);
if (!parent_iter) {
/* create a new toplevel node */
gtk_tree_store_append (GTK_TREE_STORE (cfm->contactcerts_treemodel), &iter, NULL);
gtk_tree_store_set (GTK_TREE_STORE (cfm->contactcerts_treemodel), &iter,
0, organization, -1);
/* now copy it off into parent_iter and insert it into
the hashtable */
parent_iter = gtk_tree_iter_copy (&iter);
g_hash_table_insert (cfm->contactcerts_root_hash, g_strdup (organization), parent_iter);
}
}
gtk_tree_store_append (GTK_TREE_STORE (cfm->contactcerts_treemodel), &iter, parent_iter);
if (e_cert_get_cn (cert))
gtk_tree_store_set (GTK_TREE_STORE (cfm->contactcerts_treemodel), &iter,
0, e_cert_get_cn (cert),
1, e_cert_get_email (cert),
3, cert,
-1);
else
gtk_tree_store_set (GTK_TREE_STORE (cfm->contactcerts_treemodel), &iter,
0, e_cert_get_nickname (cert),
1, e_cert_get_email (cert),
3, cert,
-1);
}
static void
@ -461,6 +562,15 @@ unload_certs (CertificateManagerData *cfm,
case E_CERT_USER:
break;
case E_CERT_CONTACT:
cfm->contactcerts_treemodel = create_contactcerts_treemodel ();
gtk_tree_view_set_model (GTK_TREE_VIEW (cfm->contactcerts_treeview),
GTK_TREE_MODEL (cfm->contactcerts_treemodel));
if (cfm->contactcerts_root_hash)
g_hash_table_destroy (cfm->contactcerts_root_hash);
cfm->contactcerts_root_hash = g_hash_table_new_full (g_str_hash, g_str_equal,
destroy_key, destroy_value);
break;
case E_CERT_SITE:
break;
@ -476,6 +586,9 @@ unload_certs (CertificateManagerData *cfm,
destroy_key, destroy_value);
break;
case E_CERT_UNKNOWN:
/* nothing to do here */
break;
}
}
@ -539,6 +652,11 @@ certificate_manager_config_control_new (void)
cfm_data->import_your_button = glade_xml_get_widget (cfm_data->gui, "your-import-button");
cfm_data->delete_your_button = glade_xml_get_widget (cfm_data->gui, "your-delete-button");
cfm_data->view_contact_button = glade_xml_get_widget (cfm_data->gui, "contact-view-button");
cfm_data->edit_contact_button = glade_xml_get_widget (cfm_data->gui, "contact-edit-button");
cfm_data->import_contact_button = glade_xml_get_widget (cfm_data->gui, "contact-import-button");
cfm_data->delete_contact_button = glade_xml_get_widget (cfm_data->gui, "contact-delete-button");
cfm_data->view_ca_button = glade_xml_get_widget (cfm_data->gui, "authority-view-button");
cfm_data->edit_ca_button = glade_xml_get_widget (cfm_data->gui, "authority-edit-button");
cfm_data->import_ca_button = glade_xml_get_widget (cfm_data->gui, "authority-import-button");

View File

@ -1512,7 +1512,7 @@
<property name="visible">True</property>
<property name="can_default">True</property>
<property name="can_focus">True</property>
<property name="label" translatable="yes">import</property>
<property name="label" translatable="yes">Import</property>
<property name="use_underline">True</property>
<property name="relief">GTK_RELIEF_NORMAL</property>
</widget>

View File

@ -22,5 +22,7 @@ noinst_LTLIBRARIES = libessmime.la
libessmime_la_SOURCES = \
e-cert.c \
e-cert.h \
e-cert-trust.c \
e-cert-trust.h \
e-cert-db.c \
e-cert-db.h

View File

@ -55,7 +55,15 @@
*
*/
/* XXX toshok why oh *why* god WHY did they do this? no fucking
sense */
/* private NSS defines used by PSM */
/* (must be declated before cert.h) */
#define CERT_NewTempCertificate __CERT_NewTempCertificate
#define CERT_AddTempCertToPerm __CERT_AddTempCertToPerm
#include "e-cert-db.h"
#include "e-cert-trust.h"
#include "nss.h"
#include "pk11func.h"
@ -187,12 +195,12 @@ e_cert_db_find_cert_by_nickname (ECertDB *certdb,
const char *nickname,
GError **error)
{
// nsNSSShutDownPreventionLock locker;
/* nsNSSShutDownPreventionLock locker;*/
CERTCertificate *cert = NULL;
//PR_LOG(gPIPNSSLog, PR_LOG_DEBUG, ("Getting \"%s\"\n", asciiname));
/*PR_LOG(gPIPNSSLog, PR_LOG_DEBUG, ("Getting \"%s\"\n", asciiname));*/
#if 0
// what it should be, but for now...
/* what it should be, but for now...*/
if (aToken) {
cert = PK11_FindCertFromNickname(asciiname, NULL);
} else {
@ -206,7 +214,7 @@ e_cert_db_find_cert_by_nickname (ECertDB *certdb,
if (cert) {
// PR_LOG(gPIPNSSLog, PR_LOG_DEBUG, ("got it\n"));
/* PR_LOG(gPIPNSSLog, PR_LOG_DEBUG, ("got it\n"));*/
ECert *ecert = e_cert_new (cert);
return ecert;
}
@ -222,7 +230,7 @@ e_cert_db_find_cert_by_key (ECertDB *certdb,
GError **error)
{
#if 0
// nsNSSShutDownPreventionLock locker;
/* nsNSSShutDownPreventionLock locker;*/
SECItem keyItem = {siBuffer, NULL, 0};
SECItem *dummy;
CERTIssuerAndSN issuerSN;
@ -237,11 +245,11 @@ e_cert_db_find_cert_by_key (ECertDB *certdb,
dummy = NSSBase64_DecodeBuffer(NULL, &keyItem, db_key,
(PRUint32)PL_strlen(db_key));
// someday maybe we can speed up the search using the moduleID and slotID
/* someday maybe we can speed up the search using the moduleID and slotID*/
moduleID = NS_NSS_GET_LONG(keyItem.data);
slotID = NS_NSS_GET_LONG(&keyItem.data[NS_NSS_LONG]);
// build the issuer/SN structure
/8 build the issuer/SN structure*/
issuerSN.serialNumber.len = NS_NSS_GET_LONG(&keyItem.data[NS_NSS_LONG*2]);
issuerSN.derIssuer.len = NS_NSS_GET_LONG(&keyItem.data[NS_NSS_LONG*3]);
issuerSN.serialNumber.data= &keyItem.data[NS_NSS_LONG*4];
@ -441,6 +449,7 @@ handle_ca_cert_download(GList *certs, GError **error)
gboolean allow;
char *nickname;
SECStatus srv;
CERTCertTrust trust;
if (!_confirm_download_ca_cert (certToShow, &trustBits, &allow)) {
/* XXX gerror */
@ -452,23 +461,28 @@ handle_ca_cert_download(GList *certs, GError **error)
return FALSE;
}
//PR_LOG(gPIPNSSLog, PR_LOG_DEBUG, ("trust is %d\n", trustBits));
/*PR_LOG(gPIPNSSLog, PR_LOG_DEBUG, ("trust is %d\n", trustBits));*/
nickname = CERT_MakeCANickname(tmpCert);
//PR_LOG(gPIPNSSLog, PR_LOG_DEBUG, ("Created nick \"%s\"\n", nickname.get()));
/*PR_LOG(gPIPNSSLog, PR_LOG_DEBUG, ("Created nick \"%s\"\n", nickname.get()));*/
#if 0
nsNSSCertTrust trust;
trust.SetValidCA();
trust.AddCATrust(trustBits & nsIX509CertDB::TRUSTED_SSL,
trustBits & nsIX509CertDB::TRUSTED_EMAIL,
trustBits & nsIX509CertDB::TRUSTED_OBJSIGN);
e_cert_trust_init (&trust);
e_cert_trust_set_valid_ca (&trust);
e_cert_trust_add_ca_trust (&trust,
#if 1
/* XXX we need that ui working i guess. */
0, 0, 0
#else
trustBits & nsIX509CertDB::TRUSTED_SSL,
trustBits & nsIX509CertDB::TRUSTED_EMAIL,
trustBits & nsIX509CertDB::TRUSTED_OBJSIGN
#endif
);
srv = CERT_AddTempCertToPerm(tmpCert,
nickname,
/*XXX trust.GetTrust()*/ 0);
&trust);
if (srv != SECSuccess) {
/* XXX gerror */
@ -479,9 +493,9 @@ handle_ca_cert_download(GList *certs, GError **error)
/* Now it's time to add the rest of the certs we just downloaded.
Since we didn't prompt the user about any of these certs, we
won't set any trust bits for them. */
nsNSSCertTrust defaultTrust;
defaultTrust.SetValidCA();
defaultTrust.AddCATrust(0,0,0);
e_cert_trust_init (&trust);
e_cert_trust_set_valid_ca (&trust);
e_cert_trusts_add_ca_trust (&trust, 0, 0, 0);
for (PRUint32 i=0; i<numCerts; i++) {
if (i == selCertIndex)
continue;
@ -494,7 +508,7 @@ handle_ca_cert_download(GList *certs, GError **error)
if (!tmpCert2) {
NS_ASSERTION(0, "Couldn't create temp cert from DER blob\n");
continue; // Let's try to import the rest of 'em
continue; /* Let's try to import the rest of 'em */
}
nickname.Adopt(CERT_MakeCANickname(tmpCert2));
CERT_AddTempCertToPerm(tmpCert2, NS_CONST_CAST(char*,nickname.get()),
@ -511,8 +525,8 @@ gboolean
e_cert_db_delete_cert (ECertDB *certdb,
ECert *ecert)
{
// nsNSSShutDownPreventionLock locker;
// nsNSSCertificate *nssCert = NS_STATIC_CAST(nsNSSCertificate*, aCert);
/* nsNSSShutDownPreventionLock locker;
nsNSSCertificate *nssCert = NS_STATIC_CAST(nsNSSCertificate*, aCert); */
CERTCertificate *cert;
SECStatus srv = SECSuccess;
@ -529,16 +543,14 @@ e_cert_db_delete_cert (ECertDB *certdb,
want to do that with user certs, because a user may re-store
the cert onto the card again at which point we *will* want to
trust that cert if it chains up properly. */
#if 0
nsNSSCertTrust trust(0, 0, 0);
CERTCertTrust trust;
e_cert_trust_init_with_values (&trust, 0, 0, 0);
srv = CERT_ChangeCertTrust(CERT_GetDefaultCertDB(),
cert, trust.GetTrust());
#endif
cert, &trust);
}
#if 0
PR_LOG(gPIPNSSLog, PR_LOG_DEBUG, ("cert deleted: %d", srv));
#endif
/*PR_LOG(gPIPNSSLog, PR_LOG_DEBUG, ("cert deleted: %d", srv));*/
return (srv) ? FALSE : TRUE;
}
@ -582,7 +594,7 @@ e_cert_db_import_certs (ECertDB *certdb,
rv = handle_ca_cert_download(certs, error);
break;
default:
// We only deal with import CA certs in this method currently.
/* We only deal with import CA certs in this method currently.*/
/* XXX gerror */
PORT_FreeArena(arena, PR_FALSE);
rv = FALSE;
@ -599,6 +611,58 @@ e_cert_db_import_email_cert (ECertDB *certdb,
char *data, guint32 length,
GError **error)
{
/*nsNSSShutDownPreventionLock locker;*/
SECStatus srv = SECFailure;
gboolean rv = TRUE;
CERTCertificate * cert;
SECItem **rawCerts;
int numcerts;
int i;
PRArenaPool *arena = PORT_NewArena(DER_DEFAULT_CHUNKSIZE);
CERTDERCerts *certCollection = e_cert_db_get_certs_from_package (arena, data, length);
if (!certCollection) {
/* XXX g_error */
PORT_FreeArena(arena, PR_FALSE);
return FALSE;
}
cert = CERT_NewTempCertificate(CERT_GetDefaultCertDB(), certCollection->rawCerts,
(char *)NULL, PR_FALSE, PR_TRUE);
if (!cert) {
/* XXX g_error */
rv = FALSE;
goto loser;
}
numcerts = certCollection->numcerts;
rawCerts = (SECItem **) PORT_Alloc(sizeof(SECItem *) * numcerts);
if ( !rawCerts ) {
/* XXX g_error */
rv = FALSE;
goto loser;
}
for ( i = 0; i < numcerts; i++ ) {
rawCerts[i] = &certCollection->rawCerts[i];
}
srv = CERT_ImportCerts(CERT_GetDefaultCertDB(), certUsageEmailSigner,
numcerts, rawCerts, NULL, PR_TRUE, PR_FALSE,
NULL);
if ( srv != SECSuccess ) {
/* XXX g_error */
rv = FALSE;
goto loser;
}
srv = CERT_SaveSMimeProfile(cert, NULL, NULL);
PORT_Free(rawCerts);
loser:
if (cert)
CERT_DestroyCertificate(cert);
if (arena)
PORT_FreeArena(arena, PR_TRUE);
return rv;
}
gboolean
@ -606,66 +670,6 @@ e_cert_db_import_user_cert (ECertDB *certdb,
char *data, guint32 length,
GError **error)
{
#if 0
/* nsNSSShutDownPreventionLock locker;*/
PK11SlotInfo *slot;
char * nickname = NULL;
gboolean rv = FALSE;
int numCACerts;
SECItem *CACerts;
CERTDERCerts * collectArgs;
CERTCertificate * cert=NULL;
collectArgs = e_cert_db_get_certs_from_package(data, length);
if (!collectArgs) {
goto loser;
}
cert = CERT_NewTempCertificate(CERT_GetDefaultCertDB(), collectArgs->rawCerts,
(char *)NULL, PR_FALSE, PR_TRUE);
if (!cert) {
goto loser;
}
slot = PK11_KeyForCertExists(cert, NULL, NULL);
if ( slot == NULL ) {
goto loser;
}
PK11_FreeSlot(slot);
/* pick a nickname for the cert */
if (cert->nickname) {
/* sigh, we need a call to look up other certs with this subject and
* identify nicknames from them. We can no longer walk down internal
* database structures rjr */
nickname = cert->nickname;
}
else {
g_assert_not_reached ();
/* nickname = default_nickname(cert, NULL); */
}
/* user wants to import the cert */
slot = PK11_ImportCertForKey(cert, nickname, NULL);
if (!slot) {
goto loser;
}
PK11_FreeSlot(slot);
numCACerts = collectArgs->numcerts - 1;
if (numCACerts) {
CACerts = collectArgs->rawCerts+1;
if ( ! CERT_ImportCAChain(CACerts, numCACerts, certUsageUserCertImport) ) {
rv = TRUE;
}
}
loser:
if ( cert ) {
CERT_DestroyCertificate(cert);
}
return rv;
#endif
}
gboolean

418
smime/lib/e-cert-trust.c Normal file
View File

@ -0,0 +1,418 @@
/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
/*
* Authors: Chris Toshok <toshok@ximian.com>
*
* Copyright (C) 2003 Novell, Inc. (www.novell.com)
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Street #330, Boston, MA 02111-1307, USA.
*
*/
/* this code is pretty much cut&pasted and renamed from mozilla.
here's their copyright/blurb */
/*
* The contents of this file are subject to the Mozilla Public
* License Version 1.1 (the "License"); you may not use this file
* except in compliance with the License. You may obtain a copy of
* the License at http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS
* IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or
* implied. See the License for the specific language governing
* rights and limitations under the License.
*
* The Original Code is the Netscape security libraries.
*
* The Initial Developer of the Original Code is Netscape
* Communications Corporation. Portions created by Netscape are
* Copyright (C) 2000 Netscape Communications Corporation. All
* Rights Reserved.
*
* Contributor(s):
* Ian McGreer <mcgreer@netscape.com>
* Javier Delgadillo <javi@netscape.com>
*
* Alternatively, the contents of this file may be used under the
* terms of the GNU General Public License Version 2 or later (the
* "GPL"), in which case the provisions of the GPL are applicable
* instead of those above. If you wish to allow use of your
* version of this file only under the terms of the GPL and not to
* allow others to use your version of this file under the MPL,
* indicate your decision by deleting the provisions above and
* replace them with the notice and other provisions required by
* the GPL. If you do not delete the provisions above, a recipient
* may use your version of this file under either the MPL or the
* GPL.
*
*/
#include "e-cert-trust.h"
void
e_cert_trust_init (CERTCertTrust *trust)
{
memset(trust, 0, sizeof(CERTCertTrust));
}
void
e_cert_trust_init_with_values (CERTCertTrust *trust,
unsigned int ssl,
unsigned int email,
unsigned int objsign)
{
memset(trust, 0, sizeof(CERTCertTrust));
e_cert_trust_add_trust(&trust->sslFlags, ssl);
e_cert_trust_add_trust(&trust->emailFlags, email);
e_cert_trust_add_trust(&trust->objectSigningFlags, objsign);
}
void
e_cert_trust_copy (CERTCertTrust *trust, CERTCertTrust *t)
{
if (t)
memcpy(trust, t, sizeof(CERTCertTrust));
else
memset(trust, 0, sizeof(CERTCertTrust));
}
void
e_cert_trust_add_ca_trust (CERTCertTrust *trust, PRBool ssl, PRBool email, PRBool objSign)
{
if (ssl) {
e_cert_trust_add_trust(&trust->sslFlags, CERTDB_TRUSTED_CA);
e_cert_trust_add_trust(&trust->sslFlags, CERTDB_TRUSTED_CLIENT_CA);
}
if (email) {
e_cert_trust_add_trust(&trust->emailFlags, CERTDB_TRUSTED_CA);
e_cert_trust_add_trust(&trust->emailFlags, CERTDB_TRUSTED_CLIENT_CA);
}
if (objSign) {
e_cert_trust_add_trust(&trust->objectSigningFlags, CERTDB_TRUSTED_CA);
e_cert_trust_add_trust(&trust->objectSigningFlags, CERTDB_TRUSTED_CLIENT_CA);
}
}
void
e_cert_trust_add_peer_trust (CERTCertTrust *trust, PRBool ssl, PRBool email, PRBool objSign)
{
if (ssl)
e_cert_trust_add_trust(&trust->sslFlags, CERTDB_TRUSTED);
if (email)
e_cert_trust_add_trust(&trust->emailFlags, CERTDB_TRUSTED);
if (objSign)
e_cert_trust_add_trust(&trust->objectSigningFlags, CERTDB_TRUSTED);
}
void
e_cert_trust_set_ssl_trust (CERTCertTrust *trust,
PRBool peer, PRBool tPeer,
PRBool ca, PRBool tCA, PRBool tClientCA,
PRBool user, PRBool warn)
{
trust->sslFlags = 0;
if (peer || tPeer)
e_cert_trust_add_trust(&trust->sslFlags, CERTDB_VALID_PEER);
if (tPeer)
e_cert_trust_add_trust(&trust->sslFlags, CERTDB_TRUSTED);
if (ca || tCA)
e_cert_trust_add_trust(&trust->sslFlags, CERTDB_VALID_CA);
if (tClientCA)
e_cert_trust_add_trust(&trust->sslFlags, CERTDB_TRUSTED_CLIENT_CA);
if (tCA)
e_cert_trust_add_trust(&trust->sslFlags, CERTDB_TRUSTED_CA);
if (user)
e_cert_trust_add_trust(&trust->sslFlags, CERTDB_USER);
if (warn)
e_cert_trust_add_trust(&trust->sslFlags, CERTDB_SEND_WARN);
}
void
e_cert_trust_set_email_trust (CERTCertTrust *trust,
PRBool peer, PRBool tPeer,
PRBool ca, PRBool tCA, PRBool tClientCA,
PRBool user, PRBool warn)
{
trust->emailFlags = 0;
if (peer || tPeer)
e_cert_trust_add_trust(&trust->emailFlags, CERTDB_VALID_PEER);
if (tPeer)
e_cert_trust_add_trust(&trust->emailFlags, CERTDB_TRUSTED);
if (ca || tCA)
e_cert_trust_add_trust(&trust->emailFlags, CERTDB_VALID_CA);
if (tClientCA)
e_cert_trust_add_trust(&trust->emailFlags, CERTDB_TRUSTED_CLIENT_CA);
if (tCA)
e_cert_trust_add_trust(&trust->emailFlags, CERTDB_TRUSTED_CA);
if (user)
e_cert_trust_add_trust(&trust->emailFlags, CERTDB_USER);
if (warn)
e_cert_trust_add_trust(&trust->emailFlags, CERTDB_SEND_WARN);
}
void
e_cert_trust_set_objsign_trust (CERTCertTrust *trust,
PRBool peer, PRBool tPeer,
PRBool ca, PRBool tCA, PRBool tClientCA,
PRBool user, PRBool warn)
{
trust->objectSigningFlags = 0;
if (peer || tPeer)
e_cert_trust_add_trust(&trust->objectSigningFlags, CERTDB_VALID_PEER);
if (tPeer)
e_cert_trust_add_trust(&trust->objectSigningFlags, CERTDB_TRUSTED);
if (ca || tCA)
e_cert_trust_add_trust(&trust->objectSigningFlags, CERTDB_VALID_CA);
if (tClientCA)
e_cert_trust_add_trust(&trust->objectSigningFlags, CERTDB_TRUSTED_CLIENT_CA);
if (tCA)
e_cert_trust_add_trust(&trust->objectSigningFlags, CERTDB_TRUSTED_CA);
if (user)
e_cert_trust_add_trust(&trust->objectSigningFlags, CERTDB_USER);
if (warn)
e_cert_trust_add_trust(&trust->objectSigningFlags, CERTDB_SEND_WARN);
}
void
e_cert_trust_set_valid_ca (CERTCertTrust *trust)
{
e_cert_trust_set_ssl_trust (trust,
PR_FALSE, PR_FALSE,
PR_TRUE, PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE);
e_cert_trust_set_email_trust (trust,
PR_FALSE, PR_FALSE,
PR_TRUE, PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE);
e_cert_trust_set_objsign_trust (trust,
PR_FALSE, PR_FALSE,
PR_TRUE, PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE);
}
void
e_cert_trust_set_trusted_server_ca (CERTCertTrust *trust)
{
e_cert_trust_set_ssl_trust (trust,
PR_FALSE, PR_FALSE,
PR_TRUE, PR_TRUE, PR_FALSE,
PR_FALSE, PR_FALSE);
e_cert_trust_set_email_trust (trust,
PR_FALSE, PR_FALSE,
PR_TRUE, PR_TRUE, PR_FALSE,
PR_FALSE, PR_FALSE);
e_cert_trust_set_objsign_trust (trust,
PR_FALSE, PR_FALSE,
PR_TRUE, PR_TRUE, PR_FALSE,
PR_FALSE, PR_FALSE);
}
void
e_cert_trust_set_trusted_ca (CERTCertTrust *trust)
{
e_cert_trust_set_ssl_trust (trust,
PR_FALSE, PR_FALSE,
PR_TRUE, PR_TRUE, PR_TRUE,
PR_FALSE, PR_FALSE);
e_cert_trust_set_email_trust (trust,
PR_FALSE, PR_FALSE,
PR_TRUE, PR_TRUE, PR_TRUE,
PR_FALSE, PR_FALSE);
e_cert_trust_set_objsign_trust (trust,
PR_FALSE, PR_FALSE,
PR_TRUE, PR_TRUE, PR_TRUE,
PR_FALSE, PR_FALSE);
}
void
e_cert_trust_set_valid_peer (CERTCertTrust *trust)
{
e_cert_trust_set_ssl_trust (trust,
PR_TRUE, PR_FALSE,
PR_FALSE, PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE);
e_cert_trust_set_email_trust (trust,
PR_TRUE, PR_FALSE,
PR_FALSE, PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE);
e_cert_trust_set_objsign_trust (trust,
PR_TRUE, PR_FALSE,
PR_FALSE, PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE);
}
void
e_cert_trust_set_valid_server_peer (CERTCertTrust *trust)
{
e_cert_trust_set_ssl_trust (trust,
PR_TRUE, PR_FALSE,
PR_FALSE, PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE);
e_cert_trust_set_email_trust (trust,
PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE);
e_cert_trust_set_objsign_trust (trust,
PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE);
}
void
e_cert_trust_set_trusted_peer (CERTCertTrust *trust)
{
e_cert_trust_set_ssl_trust (trust,
PR_TRUE, PR_TRUE,
PR_FALSE, PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE);
e_cert_trust_set_email_trust (trust,
PR_TRUE, PR_TRUE,
PR_FALSE, PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE);
e_cert_trust_set_objsign_trust (trust,
PR_TRUE, PR_TRUE,
PR_FALSE, PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE);
}
void
e_cert_trust_set_user (CERTCertTrust *trust)
{
e_cert_trust_set_ssl_trust (trust,
PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE, PR_FALSE,
PR_TRUE, PR_FALSE);
e_cert_trust_set_email_trust (trust,
PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE, PR_FALSE,
PR_TRUE, PR_FALSE);
e_cert_trust_set_objsign_trust (trust,
PR_FALSE, PR_FALSE,
PR_FALSE, PR_FALSE, PR_FALSE,
PR_TRUE, PR_FALSE);
}
PRBool
e_cert_trust_has_any_ca (CERTCertTrust *trust)
{
if (e_cert_trust_has_trust(trust->sslFlags, CERTDB_VALID_CA) ||
e_cert_trust_has_trust(trust->emailFlags, CERTDB_VALID_CA) ||
e_cert_trust_has_trust(trust->objectSigningFlags, CERTDB_VALID_CA))
return PR_TRUE;
return PR_FALSE;
}
PRBool
e_cert_trust_has_ca (CERTCertTrust *trust,
PRBool checkSSL,
PRBool checkEmail,
PRBool checkObjSign)
{
if (checkSSL && !e_cert_trust_has_trust(trust->sslFlags, CERTDB_VALID_CA))
return PR_FALSE;
if (checkEmail && !e_cert_trust_has_trust(trust->emailFlags, CERTDB_VALID_CA))
return PR_FALSE;
if (checkObjSign && !e_cert_trust_has_trust(trust->objectSigningFlags, CERTDB_VALID_CA))
return PR_FALSE;
return PR_TRUE;
}
PRBool
e_cert_trust_has_peer (CERTCertTrust *trust,
PRBool checkSSL,
PRBool checkEmail,
PRBool checkObjSign)
{
if (checkSSL && !e_cert_trust_has_trust(trust->sslFlags, CERTDB_VALID_PEER))
return PR_FALSE;
if (checkEmail && !e_cert_trust_has_trust(trust->emailFlags, CERTDB_VALID_PEER))
return PR_FALSE;
if (checkObjSign && !e_cert_trust_has_trust(trust->objectSigningFlags, CERTDB_VALID_PEER))
return PR_FALSE;
return PR_TRUE;
}
PRBool
e_cert_trust_has_any_user (CERTCertTrust *trust)
{
if (e_cert_trust_has_trust(trust->sslFlags, CERTDB_USER) ||
e_cert_trust_has_trust(trust->emailFlags, CERTDB_USER) ||
e_cert_trust_has_trust(trust->objectSigningFlags, CERTDB_USER))
return PR_TRUE;
return PR_FALSE;
}
PRBool
e_cert_trust_has_user (CERTCertTrust *trust,
PRBool checkSSL,
PRBool checkEmail,
PRBool checkObjSign)
{
if (checkSSL && !e_cert_trust_has_trust(trust->sslFlags, CERTDB_USER))
return PR_FALSE;
if (checkEmail && !e_cert_trust_has_trust(trust->emailFlags, CERTDB_USER))
return PR_FALSE;
if (checkObjSign && !e_cert_trust_has_trust(trust->objectSigningFlags, CERTDB_USER))
return PR_FALSE;
return PR_TRUE;
}
PRBool
e_cert_trust_has_trusted_ca (CERTCertTrust *trust,
PRBool checkSSL,
PRBool checkEmail,
PRBool checkObjSign)
{
if (checkSSL && !(e_cert_trust_has_trust(trust->sslFlags, CERTDB_TRUSTED_CA) ||
e_cert_trust_has_trust(trust->sslFlags, CERTDB_TRUSTED_CLIENT_CA)))
return PR_FALSE;
if (checkEmail && !(e_cert_trust_has_trust(trust->emailFlags, CERTDB_TRUSTED_CA) ||
e_cert_trust_has_trust(trust->emailFlags, CERTDB_TRUSTED_CLIENT_CA)))
return PR_FALSE;
if (checkObjSign &&
!(e_cert_trust_has_trust(trust->objectSigningFlags, CERTDB_TRUSTED_CA) ||
e_cert_trust_has_trust(trust->objectSigningFlags, CERTDB_TRUSTED_CLIENT_CA)))
return PR_FALSE;
return PR_TRUE;
}
PRBool
e_cert_trust_has_trusted_peer (CERTCertTrust *trust,
PRBool checkSSL,
PRBool checkEmail,
PRBool checkObjSign)
{
if (checkSSL && !(e_cert_trust_has_trust(trust->sslFlags, CERTDB_TRUSTED)))
return PR_FALSE;
if (checkEmail && !(e_cert_trust_has_trust(trust->emailFlags, CERTDB_TRUSTED)))
return PR_FALSE;
if (checkObjSign &&
!(e_cert_trust_has_trust(trust->objectSigningFlags, CERTDB_TRUSTED)))
return PR_FALSE;
return PR_TRUE;
}
void
e_cert_trust_add_trust (unsigned int *t, unsigned int v)
{
*t |= v;
}
PRBool
e_cert_trust_has_trust (unsigned int t, unsigned int v)
{
return (t & v);
}

86
smime/lib/e-cert-trust.h Normal file
View File

@ -0,0 +1,86 @@
/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
/*
* Authors: Chris Toshok <toshok@ximian.com>
*
* Copyright (C) 2003 Novell, Inc. (www.novell.com)
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Street #330, Boston, MA 02111-1307, USA.
*
*/
#ifndef _E_CERT_TRUST_H_
#define _E_CERT_TRUST_H_
#include <glib.h>
#include <cert.h>
#include <certdb.h>
G_BEGIN_DECLS
void e_cert_trust_init (CERTCertTrust *trust);
void e_cert_trust_init_with_values (CERTCertTrust *trust,
unsigned int ssl,
unsigned int email,
unsigned int objsign);
void e_cert_trust_copy (CERTCertTrust *dst_trust, CERTCertTrust *src_trust);
void e_cert_trust_add_ca_trust (CERTCertTrust *trust, PRBool ssl, PRBool email, PRBool objSign);
void e_cert_trust_add_peer_trust (CERTCertTrust *trust, PRBool ssl, PRBool email, PRBool objSign);
void e_cert_trust_set_ssl_trust (CERTCertTrust *trust,
PRBool peer, PRBool tPeer,
PRBool ca, PRBool tCA, PRBool tClientCA,
PRBool user, PRBool warn);
void e_cert_trust_set_email_trust (CERTCertTrust *trust,
PRBool peer, PRBool tPeer,
PRBool ca, PRBool tCA, PRBool tClientCA,
PRBool user, PRBool warn);
void e_cert_trust_set_objsign_trust (CERTCertTrust *trust,
PRBool peer, PRBool tPeer,
PRBool ca, PRBool tCA, PRBool tClientCA,
PRBool user, PRBool warn);
void e_cert_trust_set_valid_ca (CERTCertTrust *trust);
void e_cert_trust_set_trusted_server_ca (CERTCertTrust *trust);
void e_cert_trust_set_trusted_ca (CERTCertTrust *trust);
void e_cert_trust_set_valid_peer (CERTCertTrust *trust);
void e_cert_trust_set_valid_server_peer (CERTCertTrust *trust);
void e_cert_trust_set_trusted_peer (CERTCertTrust *trust);
void e_cert_trust_set_user (CERTCertTrust *trust);
PRBool e_cert_trust_has_any_ca (CERTCertTrust *trust);
PRBool e_cert_trust_has_ca (CERTCertTrust *trust,
PRBool checkSSL,
PRBool checkEmail,
PRBool checkObjSign);
PRBool e_cert_trust_has_peer (CERTCertTrust *trust,
PRBool checkSSL,
PRBool checkEmail,
PRBool checkObjSign);
PRBool e_cert_trust_has_any_user (CERTCertTrust *trust);
PRBool e_cert_trust_has_user (CERTCertTrust *trust,
PRBool checkSSL,
PRBool checkEmail,
PRBool checkObjSign);
PRBool e_cert_trust_has_trusted_ca (CERTCertTrust *trust,
PRBool checkSSL,
PRBool checkEmail,
PRBool checkObjSign);
PRBool e_cert_trust_has_trusted_peer (CERTCertTrust *trust,
PRBool checkSSL,
PRBool checkEmail,
PRBool checkObjSign);
void e_cert_trust_add_trust (unsigned int *t, unsigned int v);
PRBool e_cert_trust_has_trust (unsigned int t, unsigned int v);
G_END_DECLS
#endif /* _E_CERT_H_ */

View File

@ -56,6 +56,7 @@
*/
#include "e-cert.h"
#include "e-cert-trust.h"
#include "pk11func.h"
#include "certdb.h"
@ -219,6 +220,7 @@ e_cert_get_nickname (ECert *cert)
const char*
e_cert_get_email (ECert *cert)
{
return cert->priv->cert->emailAddr;
}
const char*
@ -269,10 +271,23 @@ e_cert_mark_for_deletion (ECert *cert)
}
ECertType
e_cert_get_cert_type (ECert *cert)
e_cert_get_cert_type (ECert *ecert)
{
if (CERT_IsCACert (cert->priv->cert, NULL))
return E_CERT_CA;
else /* XXX more here */
return E_CERT_USER;
const char *nick = e_cert_get_nickname (ecert);
const char *email = e_cert_get_email (ecert);
CERTCertificate *cert = ecert->priv->cert;
if (nick) {
if (e_cert_trust_has_any_user (cert->trust))
return E_CERT_USER;
if (e_cert_trust_has_any_ca (cert->trust)
|| CERT_IsCACert(cert,NULL))
return E_CERT_CA;
if (e_cert_trust_has_peer (cert->trust, PR_TRUE, PR_FALSE, PR_FALSE))
return E_CERT_SITE;
}
if (email && e_cert_trust_has_peer (cert->trust, PR_FALSE, PR_TRUE, PR_FALSE))
return E_CERT_CONTACT;
return E_CERT_UNKNOWN;
}

View File

@ -41,7 +41,8 @@ typedef enum {
E_CERT_CA,
E_CERT_CONTACT,
E_CERT_SITE,
E_CERT_USER
E_CERT_USER,
E_CERT_UNKNOWN
} ECertType;
struct _ECert {