rxkad_build_native_token(krb5_context context, krb5_creds *v5cred,
struct ktc_tokenUnion **tokenPtr, char **userPtr) {
char username[BUFSIZ];
- struct ktc_tokenUnion *token;
- struct token_rxkad *rxkadToken;
+ struct ktc_token token;
+ int status;
#ifdef HAVE_NO_KRB5_524
char *p;
int len;
#else
- int status;
char k4name[ANAME_SZ];
char k4inst[INST_SZ];
char k4realm[REALM_SZ];
}
#endif
- token = malloc(sizeof(struct ktc_tokenUnion));
- if (token == NULL)
- return ENOMEM;
-
- memset(token, 0, sizeof(struct ktc_tokenUnion));
-
- token->at_type = AFSTOKEN_UNION_KAD;
- rxkadToken = &token->ktc_tokenUnion_u.at_kad;
+ memset(&token, 0, sizeof(struct ktc_token));
- rxkadToken->rk_kvno = RXKAD_TKT_TYPE_KERBEROS_V5;
- rxkadToken->rk_begintime = v5cred->times.starttime;;
- rxkadToken->rk_endtime = v5cred->times.endtime;
- memcpy(&rxkadToken->rk_key, get_cred_keydata(v5cred),
+ token.kvno = RXKAD_TKT_TYPE_KERBEROS_V5;
+ token.startTime = v5cred->times.starttime;;
+ token.endTime = v5cred->times.endtime;
+ memcpy(&token.sessionKey, get_cred_keydata(v5cred),
get_cred_keylen(v5cred));
- rxkadToken->rk_ticket.rk_ticket_len = v5cred->ticket.length;
- rxkadToken->rk_ticket.rk_ticket_val = malloc(v5cred->ticket.length);
- if (rxkadToken->rk_ticket.rk_ticket_val == NULL) {
- free(token);
- return ENOMEM;
+ token.ticketLen = v5cred->ticket.length;
+ memcpy(token.ticket, v5cred->ticket.data, token.ticketLen);
+
+ status = token_importRxkadViceId(tokenPtr, &token, 0);
+ if (status) {
+ return status;
}
- memcpy(rxkadToken->rk_ticket.rk_ticket_val, v5cred->ticket.data,
- rxkadToken->rk_ticket.rk_ticket_len);
- *tokenPtr = token;
*userPtr = strdup(username);
return 0;
struct ktc_tokenUnion **tokenPtr, char **userPtr) {
CREDENTIALS cred;
char username[BUFSIZ];
- struct ktc_tokenUnion *token;
- struct token_rxkad *rxkadToken;
+ struct ktc_token token;
int status;
*tokenPtr = NULL;
strcat (username, cred.pinst);
}
- token = malloc(sizeof(struct ktc_tokenUnion));
- if (token == NULL)
- return ENOMEM;
- memset(token, 0, sizeof(struct ktc_tokenUnion));
-
- token->at_type = AFSTOKEN_UNION_KAD;
+ memset(&token, 0, sizeof(struct ktc_token));
- rxkadToken = &token->ktc_tokenUnion_u.at_kad;
- rxkadToken->rk_kvno = cred.kvno;
- rxkadToken->rk_begintime = cred.issue_date;
+ token.kvno = cred.kvno;
+ token.startTime = cred.issue_date;
/*
* It seems silly to go through a bunch of contortions to
* extract the expiration time, when the v5 credentials already
* Note that this isn't a security hole, as the expiration time
* is also contained in the encrypted token
*/
- rxkadToken->rk_endtime = v5cred->times.endtime;
- memcpy(&rxkadToken->rk_key, cred.session, 8);
- rxkadToken->rk_ticket.rk_ticket_len = cred.ticket_st.length;
- rxkadToken->rk_ticket.rk_ticket_val = malloc(cred.ticket_st.length);
- if (rxkadToken->rk_ticket.rk_ticket_val == NULL) {
- free(token);
- return ENOMEM;
+ token.endTime = v5cred->times.endtime;
+ memcpy(&token.sessionKey, cred.session, 8);
+ token.ticketLen = cred.ticket_st.length;
+ memcpy(token.ticket, cred.ticket_st.dat, token.ticketLen);
+
+ status = token_importRxkadViceId(tokenPtr, &token, 0);
+ if (status) {
+ return status;
}
- memcpy(rxkadToken->rk_ticket.rk_ticket_val, cred.ticket_st.dat,
- rxkadToken->rk_ticket.rk_ticket_len);
- *tokenPtr = token;
*userPtr = strdup(username);
return 0;
#endif /* ALLOW_REGISTER */
if ((status == 0) && (viceId != ANONYMOUSID)) {
- rxkadToken->ktc_tokenUnion_u.at_kad.rk_viceid = viceId;
- token_replaceToken(token, rxkadToken);
+ status = token_setRxkadViceId(rxkadToken, viceId);
+ if (status) {
+ fprintf(stderr, "Error %d setting rxkad ViceId\n", status);
+ status = AKLOG_SUCCESS;
+ } else {
+ token_replaceToken(token, rxkadToken);
+ }
}
}
out:
if (rxkadToken) {
- free(rxkadToken->ktc_tokenUnion_u.at_kad.rk_ticket.rk_ticket_val);
- free(rxkadToken);
+ token_freeToken(&rxkadToken);
}
if (local_cell)
return code;
}
-static void
-freeToken(struct ktc_tokenUnion *token) {
- xdr_free((xdrproc_t)xdr_ktc_tokenUnion, token);
-}
-
static int
rxkadTokenEqual(struct ktc_tokenUnion *tokenA, struct ktc_tokenUnion *tokenB) {
return (tokenA->ktc_tokenUnion_u.at_kad.rk_kvno ==
return 0;
}
+static void
+SetRxkadViceId(struct token_rxkad *rxkadToken, afs_int32 viceId)
+{
+ rxkadToken->rk_viceid = viceId;
+ if (viceId) {
+ if (((rxkadToken->rk_endtime - rxkadToken->rk_begintime) & 1) == 0) {
+ rxkadToken->rk_begintime++; /* force lifetime to be odd */
+ }
+ } else {
+ if (((rxkadToken->rk_endtime - rxkadToken->rk_begintime) & 1) == 1) {
+ rxkadToken->rk_begintime++; /* force lifetime to be even */
+ }
+ }
+}
+
+/**
+ * Import an rxkad token with a ViceId into a unified token.
+ *
+ * @param[out] atoken
+ * The resultant unified token. Free with token_freeToken.
+ * @param[in] oldToken
+ * The rxkad token to import.
+ * @param[in] viceId
+ * The optional rxkad ViceId to use. Specify 0 to explicitly not
+ * specify a ViceId.
+ *
+ * @return operation status
+ * @retval 0 success
+ */
+int
+token_importRxkadViceId(struct ktc_tokenUnion **atoken,
+ struct ktc_token *oldToken,
+ afs_int32 viceId)
+{
+ struct ktc_tokenUnion *token;
+ struct token_rxkad *rxkadToken;
+
+ token = malloc(sizeof(struct ktc_tokenUnion));
+ if (!token)
+ return ENOMEM;
+
+ token->at_type = AFSTOKEN_UNION_KAD;
+ rxkadToken = &token->ktc_tokenUnion_u.at_kad;
+
+ rxkadToken->rk_kvno = oldToken->kvno;
+ rxkadToken->rk_begintime = oldToken->startTime;
+ rxkadToken->rk_endtime = oldToken->endTime;
+ memcpy(&rxkadToken->rk_key, &oldToken->sessionKey,
+ sizeof(oldToken->sessionKey));
+ rxkadToken->rk_ticket.rk_ticket_len = oldToken->ticketLen;
+
+ rxkadToken->rk_ticket.rk_ticket_val = xdr_alloc(oldToken->ticketLen);
+ if (!rxkadToken->rk_ticket.rk_ticket_val) {
+ free(token);
+ return ENOMEM;
+ }
+ memcpy(rxkadToken->rk_ticket.rk_ticket_val, oldToken->ticket, oldToken->ticketLen);
+
+ SetRxkadViceId(rxkadToken, viceId);
+
+ *atoken = token;
+
+ return 0;
+}
+
+/**
+ * Set the optional ViceId for an rxkad token.
+ *
+ * @param[in] token
+ * The token union to change.
+ * @param[in] viceId
+ * The ViceId to set. Specify 0 to explicitly set no ViceId.
+ *
+ * @return operation status
+ * @retval EINVAL The given token union is not an rxkad token
+ * @retval 0 success
+ */
+int
+token_setRxkadViceId(struct ktc_tokenUnion *token,
+ afs_int32 viceId)
+{
+ struct token_rxkad *rxkadToken;
+
+ if (token->at_type != AFSTOKEN_UNION_KAD) {
+ return EINVAL;
+ }
+
+ rxkadToken = &token->ktc_tokenUnion_u.at_kad;
+ SetRxkadViceId(rxkadToken, viceId);
+
+ return 0;
+}
+
/*!
* Given an unified token, populate an rxkad token from it
*
found = 1;
break;
}
- freeToken(&tokenB);
+ token_freeTokenContents(&tokenB);
}
}
if (decodedOK)
- freeToken(&tokenA);
+ token_freeTokenContents(&tokenA);
if (!found)
return 0;
}
void
+token_freeTokenContents(struct ktc_tokenUnion *atoken)
+{
+ xdr_free((xdrproc_t)xdr_ktc_tokenUnion, atoken);
+}
+
+void
+token_freeToken(struct ktc_tokenUnion **atoken)
+{
+ if (*atoken) {
+ token_freeTokenContents(*atoken);
+ free(*atoken);
+ *atoken = NULL;
+ }
+}
+
+void
token_FreeSet(struct ktc_setTokenData **jar) {
if (*jar) {
xdr_free((xdrproc_t)xdr_ktc_setTokenData, *jar);