diff options
author | José Bollo <jose.bollo@iot.bzh> | 2015-12-09 14:35:04 +0100 |
---|---|---|
committer | José Bollo <jose.bollo@iot.bzh> | 2015-12-09 14:35:04 +0100 |
commit | bf7b5918fcc07713a29b9ca32f766b65b15a4ec2 (patch) | |
tree | a4ad318995f3213cee35a2065fc3c4911e2012dc /wgtpkg-digsig.c | |
parent | 0270b7281b783cbea5c1f0ebb4440d2be1bd79fa (diff) |
refactoring sources
Change-Id: Id6d52eee86b706958972e9b345ec0d4d1e488146
Signed-off-by: José Bollo <jose.bollo@iot.bzh>
Diffstat (limited to 'wgtpkg-digsig.c')
-rw-r--r-- | wgtpkg-digsig.c | 358 |
1 files changed, 0 insertions, 358 deletions
diff --git a/wgtpkg-digsig.c b/wgtpkg-digsig.c deleted file mode 100644 index 284acd1..0000000 --- a/wgtpkg-digsig.c +++ /dev/null @@ -1,358 +0,0 @@ -/* - Copyright 2015 IoT.bzh - - Licensed under the Apache License, Version 2.0 (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.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. -*/ - - -#include <string.h> -#include <syslog.h> -#include <assert.h> - -#include <libxml/parser.h> -#include <libxml/tree.h> -#include <libxml/uri.h> - - -#include "wgtpkg.h" - - - -static const char uri_role_author[] = "http://www.w3.org/ns/widgets-digsig#role-author"; -static const char uri_role_distributor[] = "http://www.w3.org/ns/widgets-digsig#role-distributor"; -static const char uri_profile[] = "http://www.w3.org/ns/widgets-digsig#profile"; - - -/* global data */ -static xmlDocPtr document; /* the document */ - -/* facility to get the first element node (skip text nodes) starting with 'node' */ -static xmlNodePtr next_element(xmlNodePtr node) -{ - while (node && node->type != XML_ELEMENT_NODE) - node = node->next; - return node; -} - -/* is the 'node' an element node of 'name'? */ -static int is_element(xmlNodePtr node, const char *name) -{ - return node->type == XML_ELEMENT_NODE - && !strcmp(name, node->name); -} - -/* is the 'node' an element node of 'name'? */ -static int is_node(xmlNodePtr node, const char *name) -{ - return node != NULL && is_element(node, name); -} - -#if 0 -/* facility to get the first element node (skip text nodes) starting with 'node' */ -static xmlNodePtr next_element_type(xmlNodePtr node, const char *name) -{ - while (node && node->type != XML_ELEMENT_NODE && strcmp(name, node->name)) - node = node->next; - return node; -} - -/* search the element node of id. NOTE : not optimized at all */ -static xmlNodePtr search_for(const char *attrname, const char *value) -{ - char *val; - xmlNodePtr iter, next; - xmlNodePtr result; - - result = NULL; - iter = xmlDocGetRootElement(document); - while (iter != NULL) { - val = xmlGetProp(iter, attrname); - if (val != NULL && !strcmp(val, value)) { - if (result != NULL) { - syslog(LOG_ERR, "duplicated %s %s", attrname, value); - free(val); - return NULL; - } - result = iter; - } - free(val); - next = next_element(iter->children); - if (next == NULL) { - /* no child, try sibling */ - next = next_element(iter->next); - if (next == NULL) { - iter = iter->parent; - while (iter != NULL && next == NULL) { - next = next_element(iter->next); - iter = iter->parent; - } - } - } - iter = next; - } - if (result == NULL) - syslog(LOG_ERR, "node of %s '%s' not found", attrname, value); - return result; -} - -/* search the element node of id. NOTE : not optimized at all */ -static xmlNodePtr search_id(const char *id) -{ - return search_for("Id", id); -} -#endif - -/* check the digest of one element */ -static int check_one_reference(xmlNodePtr ref) -{ - int rc; - char *uri; - xmlURIPtr u; - struct filedesc *fdesc; - - /* start */ - rc = -1; - - /* get the uri */ - uri = xmlGetProp(ref, "URI"); - if (uri == NULL) { - syslog(LOG_ERR, "attribute URI of element <Reference> not found"); - goto error; - } - - /* parse the uri */ - u = xmlParseURI(uri); - if (!u) { - syslog(LOG_ERR, "error while parsing URI %s", uri); - goto error2; - } - - /* check that unexpected parts are not there */ - if (u->scheme || u->opaque || u->authority || u->server || u->user || u->query) { - syslog(LOG_ERR, "unexpected uri component in %s", uri); - goto error3; - } - - /* check path and fragment */ - if (!u->path && !u->fragment) { - syslog(LOG_ERR, "invalid uri %s", uri); - goto error3; - } - if (u->path && u->fragment) { - syslog(LOG_ERR, "not allowed to sign foreign fragment in %s", uri); - goto error3; - } - - if (u->path) { - /* check that the path is valid */ - fdesc = file_of_name(u->path); - if (fdesc == NULL) { - syslog(LOG_ERR, "reference to unknown file %s", u->path); - goto error3; - } - if (fdesc->type != type_file) { - syslog(LOG_ERR, "reference to directory %s", u->path); - goto error3; - } - if ((fdesc->flags & flag_distributor_signature) != 0) { - syslog(LOG_ERR, "reference to signature %s", u->path); - goto error3; - } - fdesc->flags |= flag_referenced; - rc = 0; - } else { - rc = 0; - } - -error3: - xmlFreeURI(u); -error2: - xmlFree(uri); -error: - return rc; -} - -static int check_references(xmlNodePtr sinfo) -{ - xmlNodePtr elem; - - elem = sinfo->children; - while (elem != NULL) { - if (is_element(elem, "Reference")) - if (check_one_reference(elem)) - return -1; - elem = elem->next; - } - return 0; -} - -static int get_certificates(xmlNodePtr kinfo) -{ - xmlNodePtr n1, n2; - char *b; - int rc; - - n1 = kinfo->children; - while (n1) { - if (is_element(n1, "X509Data")) { - n2 = n1->children; - while (n2) { - if (is_element(n2, "X509Certificate")) { - b = xmlNodeGetContent(n2); - if (b == NULL) { - syslog(LOG_ERR, "xmlNodeGetContent of X509Certificate failed"); - return -1; - } - rc = add_certificate_b64(b); - xmlFree(b); - if (rc) - return rc; - } - n2 = n2->next; - } - } - n1 = n1->next; - } - return 0; -} - -/* checks the current document */ -static int checkdocument() -{ - int rc; - xmlNodePtr sinfo, svalue, kinfo, objs, rootsig; - - rc = -1; - - rootsig = xmlDocGetRootElement(document); - if (!is_node(rootsig, "Signature")) { - syslog(LOG_ERR, "root element <Signature> not found"); - goto error; - } - - sinfo = next_element(rootsig->children); - if (!is_node(sinfo, "SignedInfo")) { - syslog(LOG_ERR, "element <SignedInfo> not found"); - goto error; - } - - svalue = next_element(sinfo->next); - if (!is_node(svalue, "SignatureValue")) { - syslog(LOG_ERR, "element <SignatureValue> not found"); - goto error; - } - - kinfo = next_element(svalue->next); - if (is_node(kinfo, "KeyInfo")) { - objs = kinfo->next; - } else { - objs = kinfo; - kinfo = NULL; - } - - rc = check_references(sinfo); - if (rc) - goto error; - - rc = xmlsec_verify(rootsig); - if (rc) - goto error; - - rc = get_certificates(kinfo); - -error: - return rc; -} - -/* verify the digital signature of the file described by 'fdesc' */ -int verify_digsig(struct filedesc *fdesc) -{ - int res; - - assert ((fdesc->flags & flag_signature) != 0); - debug("-- checking file %s",fdesc->name); - - /* reset the flags */ - file_clear_flags(); - clear_certificates(); - - /* reads and xml parses the signature file */ - document = xmlReadFile(fdesc->name, NULL, 0); - if (document == NULL) { - syslog(LOG_ERR, "xml parse of file %s failed", fdesc->name); - return -1; - } - - res = checkdocument(); - if (res) - syslog(LOG_ERR, "previous error was during check of file %s", fdesc->name); - - xmlFreeDoc(document); - return res; -} - -/* check all the signature files */ -int check_all_signatures() -{ - int rc, irc; - unsigned int i, n; - struct filedesc *fdesc; - - n = signature_count(); - rc = 0; - for (i = n ; i-- > 0 ; ) { - fdesc = signature_of_index(i); - irc = verify_digsig(fdesc); - if (!irc) - rc = irc; - } - - return rc; -} - -/* create a signature of 'index' (0 for author, other values for distributors) -using the private 'key' (filename) and the certificates 'certs' (filenames) -as trusted chain */ -int create_digsig(int index, const char *key, const char **certs) -{ - struct filedesc *fdesc; - xmlDocPtr doc; - int rc, len; - - rc = -1; - - /* create the doc */ - doc = xmlsec_create(index, key, certs); - if (doc == NULL) - goto error; - - /* instanciate the filename */ - fdesc = create_signature(index); - if (fdesc == NULL) - goto error2; - - /* save the doc as file */ - len = xmlSaveFormatFileEnc(fdesc->name, doc, NULL, 0); - if (len < 0) { - syslog(LOG_ERR, "xmlSaveFormatFileEnc to %s failed", fdesc->name); - goto error2; - } - - rc = 0; -error2: - xmlFreeDoc(doc); -error: - return rc; -} - - |