summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDan McGee <dan@archlinux.org>2011-04-22 02:01:06 +0200
committerDan McGee <dan@archlinux.org>2011-04-24 17:48:33 +0200
commit31e55b8049ed001a993441f3efc8ffebdf360061 (patch)
treeef01f59eed8cdbf5d5e9f76c1500b9ef30ed67e9
parenta7d33d0c36420462b3de5c7e2f8327ddbda2a129 (diff)
downloadpacman-31e55b8049ed001a993441f3efc8ffebdf360061.tar.gz
pacman-31e55b8049ed001a993441f3efc8ffebdf360061.tar.xz
signing: let GPGME handle loading signatures from files
Rather than go through all the hassle of doing this ourselves, just let GPGME handle the work by passing it a file handle. Signed-off-by: Dan McGee <dan@archlinux.org>
-rw-r--r--lib/libalpm/be_package.c6
-rw-r--r--lib/libalpm/db.c23
-rw-r--r--lib/libalpm/db.h3
-rw-r--r--lib/libalpm/signing.c94
-rw-r--r--lib/libalpm/signing.h1
5 files changed, 35 insertions, 92 deletions
diff --git a/lib/libalpm/be_package.c b/lib/libalpm/be_package.c
index 8a6ed6c4..6e65c7dd 100644
--- a/lib/libalpm/be_package.c
+++ b/lib/libalpm/be_package.c
@@ -243,18 +243,12 @@ static pmpkg_t *pkg_load(const char *pkgfile, int full)
/* attempt to stat the package file, ensure it exists */
if(stat(pkgfile, &st) == 0) {
- int sig_ret;
-
newpkg = _alpm_pkg_new();
if(newpkg == NULL) {
RET_ERR(PM_ERR_MEMORY, NULL);
}
newpkg->filename = strdup(pkgfile);
newpkg->size = st.st_size;
-
- /* TODO: do something with ret value */
- sig_ret = _alpm_load_signature(pkgfile, &(newpkg->pgpsig));
- (void)sig_ret;
} else {
/* couldn't stat the pkgfile, return an error */
RET_ERR(PM_ERR_PKG_OPEN, NULL);
diff --git a/lib/libalpm/db.c b/lib/libalpm/db.c
index f5e7a25f..3d593b36 100644
--- a/lib/libalpm/db.c
+++ b/lib/libalpm/db.c
@@ -314,27 +314,6 @@ pmdb_t *_alpm_db_new(const char *treename, int is_local)
return db;
}
-const pmpgpsig_t *_alpm_db_pgpsig(pmdb_t *db)
-{
- ALPM_LOG_FUNC;
-
- /* Sanity checks */
- ASSERT(db != NULL, return(NULL));
-
- if(db->pgpsig.data == NULL) {
- const char *dbfile;
- int ret;
-
- dbfile = _alpm_db_path(db);
-
- /* TODO: do something with ret value */
- ret = _alpm_load_signature(dbfile, &(db->pgpsig));
- (void)ret;
- }
-
- return &(db->pgpsig);
-}
-
void _alpm_db_free(pmdb_t *db)
{
ALPM_LOG_FUNC;
@@ -343,8 +322,6 @@ void _alpm_db_free(pmdb_t *db)
_alpm_db_free_pkgcache(db);
/* cleanup server list */
FREELIST(db->servers);
- /* only need to free data */
- FREE(db->pgpsig.data);
FREE(db->_path);
FREE(db->treename);
FREE(db);
diff --git a/lib/libalpm/db.h b/lib/libalpm/db.h
index 204a0be0..399e2d56 100644
--- a/lib/libalpm/db.h
+++ b/lib/libalpm/db.h
@@ -63,8 +63,6 @@ struct __pmdb_t {
pmpkghash_t *pkgcache;
alpm_list_t *grpcache;
alpm_list_t *servers;
- /* do not access directly, use _alpm_db_pgpsig(db) for lazy access */
- pmpgpsig_t pgpsig;
pgp_verify_t pgp_verify;
struct db_operations *ops;
@@ -81,7 +79,6 @@ alpm_list_t *_alpm_db_search(pmdb_t *db, const alpm_list_t *needles);
pmdb_t *_alpm_db_register_local(void);
pmdb_t *_alpm_db_register_sync(const char *treename);
void _alpm_db_unregister(pmdb_t *db);
-const pmpgpsig_t *_alpm_db_pgpsig(pmdb_t *db);
/* be_*.c, backend specific calls */
int _alpm_local_db_read(pmdb_t *db, pmpkg_t *info, pmdbinfrq_t inforeq);
diff --git a/lib/libalpm/signing.c b/lib/libalpm/signing.c
index 9d4fd076..28b7ad98 100644
--- a/lib/libalpm/signing.c
+++ b/lib/libalpm/signing.c
@@ -92,9 +92,10 @@ error:
}
/**
- * Check the PGP package signature for the given file.
+ * Check the PGP signature for the given file.
* @param path the full path to a file
- * @param sig PGP signature data in raw form (already decoded)
+ * @param sig PGP signature data in raw form (already decoded); if NULL, expect
+ * a signature file next to 'path'
* @return a int value : 0 (valid), 1 (invalid), -1 (an error occured)
*/
int _alpm_gpgme_checksig(const char *path, const pmpgpsig_t *sig)
@@ -105,16 +106,28 @@ int _alpm_gpgme_checksig(const char *path, const pmpgpsig_t *sig)
gpgme_data_t filedata, sigdata;
gpgme_verify_result_t result;
gpgme_signature_t gpgsig;
+ char *sigpath = NULL;
FILE *file = NULL, *sigfile = NULL;
ALPM_LOG_FUNC;
- if(!sig || !sig->data) {
- RET_ERR(PM_ERR_SIG_UNKNOWN, -1);
- }
if(!path || access(path, R_OK) != 0) {
RET_ERR(PM_ERR_NOT_A_FILE, -1);
}
+
+ if(!sig) {
+ size_t len = strlen(path) + 5;
+ CALLOC(sigpath, len, sizeof(char), RET_ERR(PM_ERR_MEMORY, -1));
+ snprintf(sigpath, len, "%s.sig", path);
+
+ if(!access(sigpath, R_OK) == 0) {
+ FREE(sigpath);
+ RET_ERR(PM_ERR_SIG_UNKNOWN, -1);
+ }
+ } else if(!sig->data) {
+ RET_ERR(PM_ERR_SIG_UNKNOWN, -1);
+ }
+
if(gpgme_init()) {
/* pm_errno was set in gpgme_init() */
return -1;
@@ -140,7 +153,19 @@ int _alpm_gpgme_checksig(const char *path, const pmpgpsig_t *sig)
CHECK_ERR();
/* next create data object for the signature */
- err = gpgme_data_new_from_mem(&sigdata, (char *)sig->data, sig->len, 0);
+ if(sig) {
+ /* memory-based, we loaded it from a sync DB */
+ err = gpgme_data_new_from_mem(&sigdata, (char *)sig->data, sig->len, 0);
+ } else {
+ /* file-based, it is on disk */
+ sigfile = fopen(sigpath, "rb");
+ if(sigfile == NULL) {
+ pm_errno = PM_ERR_NOT_A_FILE;
+ ret = -1;
+ goto error;
+ }
+ err = gpgme_data_new_from_stream(&sigdata, sigfile);
+ }
CHECK_ERR();
/* here's where the magic happens */
@@ -196,6 +221,7 @@ error:
if(file) {
fclose(file);
}
+ FREE(sigpath);
if(err != GPG_ERR_NO_ERROR) {
_alpm_log(PM_LOG_ERROR, _("GPGME error: %s\n"), gpgme_strerror(err));
RET_ERR(PM_ERR_GPGME, -1);
@@ -204,55 +230,6 @@ error:
}
/**
- * Load the signature from the given path into the provided struct.
- * @param sigfile the signature to attempt to load
- * @param pgpsig the struct to place the data in
- *
- * @return 0 on success, 1 on file not found, -1 on error
- */
-int _alpm_load_signature(const char *file, pmpgpsig_t *pgpsig) {
- struct stat st;
- char *sigfile;
- int ret = -1;
-
- /* look around for a PGP signature file; load if available */
- MALLOC(sigfile, strlen(file) + 5, RET_ERR(PM_ERR_MEMORY, -1));
- sprintf(sigfile, "%s.sig", file);
-
- if(access(sigfile, R_OK) == 0 && stat(sigfile, &st) == 0) {
- FILE *f;
- size_t bytes_read;
-
- if(st.st_size > 4096 || (f = fopen(sigfile, "rb")) == NULL) {
- free(sigfile);
- return ret;
- }
- CALLOC(pgpsig->data, st.st_size, sizeof(unsigned char),
- RET_ERR(PM_ERR_MEMORY, -1));
- bytes_read = fread(pgpsig->data, sizeof(char), st.st_size, f);
- if(bytes_read == (size_t)st.st_size) {
- pgpsig->len = bytes_read;
- _alpm_log(PM_LOG_DEBUG, "loaded gpg signature file, location %s\n",
- sigfile);
- ret = 0;
- } else {
- _alpm_log(PM_LOG_WARNING, _("Failed reading PGP signature file %s"),
- sigfile);
- FREE(pgpsig->data);
- }
-
- fclose(f);
- } else {
- _alpm_log(PM_LOG_DEBUG, "signature file %s not found\n", sigfile);
- /* not fatal...we return a different error code here */
- ret = 1;
- }
-
- free(sigfile);
- return ret;
-}
-
-/**
* Determines the necessity of checking for a valid PGP signature
* @param db the sync database to query
*
@@ -271,7 +248,7 @@ pgp_verify_t _alpm_db_get_sigverify_level(pmdb_t *db)
}
/**
- * Check the PGP package signature for the given package file.
+ * Check the PGP signature for the given package file.
* @param pkg the package to check
* @return a int value : 0 (valid), 1 (invalid), -1 (an error occurred)
*/
@@ -285,7 +262,7 @@ int SYMEXPORT alpm_pkg_check_pgp_signature(pmpkg_t *pkg)
}
/**
- * Check the PGP package signature for the given database.
+ * Check the PGP signature for the given database.
* @param db the database to check
* @return a int value : 0 (valid), 1 (invalid), -1 (an error occurred)
*/
@@ -294,8 +271,7 @@ int SYMEXPORT alpm_db_check_pgp_signature(pmdb_t *db)
ALPM_LOG_FUNC;
ASSERT(db != NULL, return 0);
- return _alpm_gpgme_checksig(_alpm_db_path(db),
- _alpm_db_pgpsig(db));
+ return _alpm_gpgme_checksig(_alpm_db_path(db), NULL);
}
/* vim: set ts=2 sw=2 noet: */
diff --git a/lib/libalpm/signing.h b/lib/libalpm/signing.h
index a378fa50..5976cf2a 100644
--- a/lib/libalpm/signing.h
+++ b/lib/libalpm/signing.h
@@ -32,7 +32,6 @@ struct __pmpgpsig_t {
};
int _alpm_gpgme_checksig(const char *path, const pmpgpsig_t *sig);
-int _alpm_load_signature(const char *sigfile, pmpgpsig_t *pgpsig);
pgp_verify_t _alpm_db_get_sigverify_level(pmdb_t *db);
#endif /* _ALPM_SIGNING_H */