void rex_mkkeys (rpc_bytes<> *ksc, rpc_bytes<> *kcs, sfs_hash *sessid, sfs_seqno seqno, const sfs_kmsg &sdat, const sfs_kmsg &cdat) { sfs_sessinfo sess; sess.type = SFS_SESSINFO; rex_sesskeydat skd; skd.seqno = seqno; skd.type = SFS_KCS; sess.kcs.setsize (sha1::hashsize); sha1_hmacxdr_2 (sess.kcs.base (), sdat.kcs_share.base (), sdat.kcs_share.size (), cdat.kcs_share.base (), cdat.kcs_share.size (), skd, true); skd.type = SFS_KSC; sess.ksc.setsize (sha1::hashsize); sha1_hmacxdr_2 (sess.ksc.base (), sdat.ksc_share.base (), sdat.ksc_share.size (), cdat.ksc_share.base (), cdat.ksc_share.size (), skd, true); if (sessid) sha1_hashxdr (sessid->base (), sess, true); if (kcs) swap (*kcs, sess.kcs); if (ksc) swap (*ksc, sess.ksc); bzero (sess.kcs.base (), sess.kcs.size ()); bzero (sess.ksc.base (), sess.ksc.size ()); }
static str hash_sprivk (const sfs_2schnorr_priv_xdr &k) { sfs_hash h; if (!sha1_hashxdr (&h, k)) return NULL; return str (h.base (), h.size ()); }
void rex_mksecretid (vec<char> &secretid, rpc_bytes<> &ksc, rpc_bytes<> &kcs) { sfs_sessinfo si; si.type = SFS_SESSINFO_SECRETID; si.ksc = ksc; si.kcs = kcs; sfs_hash dummy_hash; secretid.setsize (dummy_hash.size ()); sha1_hashxdr (secretid.base (), si, true); bzero (si.kcs.base (), si.kcs.size ()); bzero (si.ksc.base (), si.ksc.size ()); }
void sfsproac::authinit (svccb *sbp) { sfsextauth_init *aa = sbp->Xtmpl getarg<sfsextauth_init> (); ptr<sfs_authreq2> authreq = New refcounted<sfs_authreq2>; authreq->type = SFS_SIGNED_AUTHREQ; authreq->user = user; authreq->seqno = aa->autharg.seqno; if (!sha1_hashxdr (authreq->authid.base (), aa->autharg.authinfo)) { warn << "Could not hash authinfo into authid.\n"; sfsagent_auth_res res; res.set_authenticate (false); sbp->replyref (res); return; } sfsauth2_sigreq sr; sr.set_type (SFS_SIGNED_AUTHREQ); *sr.authreq = *authreq; privk->sign (sr, aa->autharg.authinfo, wrap (this, &sfsproac::authinitcb, sbp, authreq)); return; }
void authclnt::sfsauth_sign (svccb *sbp) { sfsauth2_sign_arg *arg = sbp->Xtmpl getarg<sfsauth2_sign_arg> (); sfsauth2_sign_res res (true); u_int32_t authno = sbp->getaui (); sfsauth_dbrec db; bool restricted_sign = false; urec_t *ur = NULL; sfsauth_keyhalf *kh = NULL; sfs_idname uname; if (authno && (ur = utab[authno])) { kh = &ur->kh; uname = ur->uname; } if (!kh && arg->req.type == SFS_SIGNED_AUTHREQ && arg->req.authreq->type == SFS_SIGNED_AUTHREQ_NOCRED && arg->authinfo.service == SFS_AUTHSERV && authid == arg->req.authreq->authid) { sfsauth_dbkey key (SFSAUTH_DBKEY_NAME); if ((*key.name = arg->user) && get_user_cursor (NULL, NULL, &db, key)) { kh = &db.userinfo->srvprivkey; uname = db.userinfo->name; restricted_sign = true; } } if (!kh || kh->type != SFSAUTH_KEYHALF_PRIV) { res.set_ok (false); *res.errmsg = "No valid server private keyhalf for user"; sbp->replyref (res); return; } if (arg->presig.type != SFS_2SCHNORR) { res.set_ok (false); *res.errmsg = "Can only answer 2-Schnorr requests"; sbp->replyref (res); return; } res.sig->set_type (SFS_SCHNORR); int i = sfs_schnorr_pub::find (*kh, arg->pubkeyhash); if (i < 0) { res.set_ok (false); *res.errmsg = "No matching keyhalf found on server."; sbp->replyref (res); return; } const sfs_2schnorr_priv_xdr &spriv = (*kh->priv)[i]; if (ur && !sprivk_tab.is_valid (hash_sprivk (spriv))) { res.set_ok (false); *res.errmsg = "Server keyhalf is no longer valid."; sbp->replyref (res); return; } ref<schnorr_srv_priv> srv_key = New refcounted<schnorr_srv_priv> (spriv.p, spriv.q, spriv.g, spriv.y, spriv.x); str msg = sigreq2str (arg->req); if (!msg) { res.set_ok (false); *res.errmsg = "Cannot marshal signature request"; sbp->replyref (res); return ; } sfs_hash aid_tmp; if (arg->req.type != SFS_NULL && (!sha1_hashxdr (aid_tmp.base (), arg->authinfo) || !sigreq_authid_cmp (arg->req, aid_tmp))) { res.set_ok (false); *res.errmsg = "Incorrect authid in request"; sbp->replyref (res); return ; } if (!siglog (siglogline (*arg, uname))) { res.set_ok (false); *res.errmsg = "Refusing to sign: could not log signature"; sbp->replyref (res); return; } srv_key->endorse_signature (&res.sig->schnorr->r, &res.sig->schnorr->s, msg, arg->presig.schnorr->r); sbp->replyref (res); }