]> git.sommitrealweird.co.uk Git - onak.git/blob - cleankey.c
d4046f3e47dd6529bdae02b78a222bacb4a2fe01
[onak.git] / cleankey.c
1 /*
2  * cleankey.c - Routines to look for common key problems and clean them up.
3  *
4  * Copyright 2004 Jonathan McDowell <noodles@earth.li>
5  *
6  * This program is free software: you can redistribute it and/or modify it
7  * under the terms of the GNU General Public License as published by the Free
8  * Software Foundation; version 2 of the License.
9  *
10  * This program is distributed in the hope that it will be useful, but WITHOUT
11  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12  * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
13  * more details.
14  *
15  * You should have received a copy of the GNU General Public License along with
16  * this program; if not, write to the Free Software Foundation, Inc., 51
17  * Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
18  */
19
20 #include <stdbool.h>
21 #include <stdio.h>
22 #include <stdlib.h>
23
24 #include "cleankey.h"
25 #include "keystructs.h"
26 #include "mem.h"
27 #include "merge.h"
28 #include "log.h"
29
30 /**
31  *      dedupuids - Merge duplicate uids on a key.
32  *      @key: The key to de-dup uids on.
33  *
34  *      This function attempts to merge duplicate IDs on a key. It returns 0
35  *      if the key is unchanged, otherwise the number of dups merged.
36  */
37 int dedupuids(struct openpgp_publickey *key)
38 {
39         struct openpgp_signedpacket_list *curuid = NULL;
40         struct openpgp_signedpacket_list *dup = NULL;
41         struct openpgp_signedpacket_list *tmp = NULL;
42         int                               merged = 0;
43
44         log_assert(key != NULL);
45         curuid = key->uids;
46         while (curuid != NULL) {
47                 dup = find_signed_packet(curuid->next, curuid->packet);
48                 while (dup != NULL) {
49                         logthing(LOGTHING_INFO, "Found duplicate uid: %.*s",
50                                         curuid->packet->length,
51                                         curuid->packet->data);
52                         merged++;
53                         merge_packet_sigs(curuid, dup);
54                         /*
55                          * Remove the duplicate uid.
56                          */
57                         tmp = curuid;
58                         while (tmp != NULL && tmp->next != dup) {
59                                 tmp = tmp->next;
60                         }
61                         log_assert(tmp != NULL);
62                         tmp->next = dup->next;
63                         dup->next = NULL;
64                         free_signedpacket_list(dup);
65
66                         dup = find_signed_packet(curuid->next, curuid->packet);
67                 }
68                 curuid = curuid->next;
69         }
70
71         return merged;
72 }
73
74 /**
75  *      cleankeys - Apply all available cleaning options on a list of keys.
76  *      @keys: The list of keys to clean.
77  *
78  *      Applies all the cleaning options we can (eg duplicate key ids) to a
79  *      list of keys. Returns 0 if no changes were made, otherwise the number
80  *      of keys cleaned.
81  */
82 int cleankeys(struct openpgp_publickey *keys)
83 {
84         int changed = 0;
85
86         while (keys != NULL) {
87                 if (dedupuids(keys) > 0) {
88                         changed++;
89                 }
90                 keys = keys->next;
91         }
92
93         return changed;
94 }