--- pgp/src/keymaint.c 2018/04/24 16:39:17 1.1.1.3 +++ pgp/src/keymaint.c 2018/04/24 16:40:06 1.1.1.4 @@ -89,6 +89,7 @@ static VOID * allocn(int size); static char * store_str(char *str); static VOID * allocbuf(int size); static void freebufpool(void); +static void compute_legit(struct userid *id); #define ALLOC_UNIT 4000 /* memory will be allocated in chunks of this size */ @@ -147,7 +148,7 @@ static boolean check_only = FALSE; static boolean mverbose; static FILE *sec_fp; static FILE *floppy_fp = NULL; - +static int undefined_trust; /* number of complete keys with undef. trust */ /* * Update trust parameters in a keyring, should be called after all @@ -174,6 +175,7 @@ maint_check(char *ringfile, int options) char *fixfile; mverbose = ((options & MAINT_VERBOSE) != 0); + if (moreflag) open_more(); if (*floppyring != '\0' && (floppy_fp = fopen(floppyring, FOPRBIN)) == NULL) @@ -201,6 +203,30 @@ maint_check(char *ringfile, int options) pgpout = sav; } #endif + /* Inform user of trust parameters to be changed... */ + if (undefined_trust) { + + /* If we are just going to check, then exit now... */ + if (options & MAINT_CHECK){ + maint_list(ringfile); + } + + fprintf(pgpout, PSTR("\n%d \"trust parameter(s)\" need to be changed.\n"), + undefined_trust); + + if (options & MAINT_CHECK) { + close_more(); + return status; + } + + fprintf(pgpout, PSTR("Continue with '%s' (Y/n)? "), + ringfile); + if (!getyesno('y')) { + close_more(); + return status; + } + } + /* do the fixes in a scratch file */ fixfile = tempfile(0); if (copyfiles_by_name(ringfile, fixfile) < 0) { @@ -228,10 +254,10 @@ maintenance(char *ringfile) { int status; char secretkeyring[MAX_PATH]; + undefined_trust = 0; /* None so far... */ if (max_cert_depth > MAX_DEPTH) max_cert_depth = MAX_DEPTH; - buildfilename(secretkeyring, SECRET_KEYRING_FILENAME); if ((sec_fp = fopen(secretkeyring, FOPRBIN)) == NULL) fprintf(pgpout,PSTR("\nCan't open secret key ring file '%s'\n"), @@ -263,7 +289,7 @@ maintenance(char *ringfile) endkrent(); maint_release_mem(); - return(status); + return(status+undefined_trust); failed: if (verbose) @@ -485,21 +511,39 @@ trace_sig_chain(struct pubkey *pk, int d int counts[MAX_DEPTH]; struct signature *sig, *s; struct pubkey *p; + struct userid *id; assert(depth <= max_cert_depth); if (pk->pk_depth && pk->pk_depth <= depth) return 0; pk->pk_depth = depth; + /* Should we ask for trust. If this key is legit, then go for + * it! Ask the user.... + */ + if (TRUST_LEV(pk->pk_owntrust) == KC_OWNERTRUST_UNDEFINED) + for (id = pk->pk_userids; id; id = id->uid_next) { + compute_legit(id); + if ((id->uid_legit & KC_LEGIT_MASK) == + KC_LEGIT_COMPLETE) { + SET_TRUST(&pk->pk_owntrust, + ask_owntrust(user_from_keyID(pk->pk_keyid), + pk->pk_owntrust)); + break; + } + } + + /* Return if I haven't signed anyone's keys, since I + * don't need to check any further.. -warlord 93-04-11 + */ + if (!pk->pk_signed) + return 0; + #ifdef DEBUG if (mverbose) fprintf(pgpout, "%*s%d-v %s\n", 2*depth, "", depth, pk->pk_userids->uid_userid); #endif - if (pk->pk_signed && TRUST_LEV(pk->pk_owntrust) == KC_OWNERTRUST_UNDEFINED) - SET_TRUST(&pk->pk_owntrust, - ask_owntrust(user_from_keyID(pk->pk_keyid), pk->pk_owntrust)); - /* all keys signed by pk */ for (sig = pk->pk_signed; sig; sig = sig->sig_nextfrom) { if (mverbose) @@ -510,8 +554,6 @@ trace_sig_chain(struct pubkey *pk, int d sig->sig_trust |= KC_CONTIG; /* CONTIG bit currently unused */ p = sig->sig_uid->uid_key; /* this key signed by pk */ - if (!p->pk_signed) - continue; /* didn't sign anything */ if (p->pk_owntrust & KC_BUCKSTOP) continue; /* will be handled from main loop */ if (p->pk_depth && p->pk_depth <= depth+1) @@ -549,7 +591,7 @@ trace_sig_chain(struct pubkey *pk, int d * compute validity of userid/key pair, the number of signatures and the * trust level of these signatures determines the validity. */ -void +static void compute_legit(struct userid *id) { struct signature *s; @@ -735,7 +777,7 @@ maint_list(char *ringfile) userid[0] = '\0'; break; case CTB_USERID_TYPE: - if (!usercount) { /* first userid */ + if (!usercount) { /* first userid */ fprintf(pgpout, "%c %s ", tchar, keyIDstring(keyID)); fprintf(pgpout, " %-*s", trustlst_len, trust_lst[owntrust]); } else @@ -949,6 +991,7 @@ this key's owner to certify other keys. if (check_only || filter_mode || batchmode) { /* not interactive */ + ++undefined_trust; /* We complete/undefined. Why? */ return(KC_OWNERTRUST_UNDEFINED); } @@ -1072,6 +1115,9 @@ static char *sigtrust_msg[] = { * * 'what' can also be SHOW_LISTFMT to get the same format as for pgp -kv * no signatures or extra userids will be printed in this case. + * + * 'what' can be SHOW_CHANGE, in which case it will take the keyID and + * call show_update(); */ int show_key(FILE *f, long keypos, int what) @@ -1117,6 +1163,10 @@ show_key(FILE *f, long keypos, int what) { if (userids == 0) { PascalToC(userid); /* for display */ ++userids; + if (what & SHOW_CHANGE) { + show_update(key2IDstring(n)); + break; + } if (what & SHOW_LISTFMT) { if (is_ctb_type(keyctb,CTB_CERT_PUBKEY_TYPE)) fprintf(pgpout,"pub"); @@ -1170,6 +1220,10 @@ show_key(FILE *f, long keypos, int what) { if (userids == 0) compromised = 1; + if (what & SHOW_CHANGE) { + show_update(key2IDstring(n)); + break; + } if (what & SHOW_SIGS) { if (print_trust) { read_trust(f, &keyctrl); @@ -1188,6 +1242,14 @@ show_key(FILE *f, long keypos, int what) return(status); } /* show_key */ +/* show_update -- this function just prints an update message to + * pgpout to inform the user that an update happened. + */ +void +show_update(char *s) +{ + fprintf(pgpout, "Updated keyID: 0x%s\n", s); +} /*