38 #include <linux/module.h>
40 #include <linux/types.h>
41 #include <linux/slab.h>
49 # define RPCDBG_FACILITY RPCDBG_AUTH
52 static struct gss_api_mech gss_kerberos_mech;
61 .name =
"des-cbc-crc",
62 .encrypt_name =
"cbc(des)",
83 .encrypt_name =
"ecb(arc4)",
84 .cksum_name =
"hmac(md5)",
103 .name =
"des3-hmac-sha1",
104 .encrypt_name =
"cbc(des3_ede)",
105 .cksum_name =
"hmac(sha1)",
124 .name =
"aes128-cts",
125 .encrypt_name =
"cts(cbc(aes))",
126 .cksum_name =
"hmac(sha1)",
147 .name =
"aes256-cts",
148 .encrypt_name =
"cts(cbc(aes))",
149 .cksum_name =
"hmac(sha1)",
166 static const int num_supported_enctypes =
170 supported_gss_krb5_enctype(
int etype)
173 for (i = 0; i < num_supported_enctypes; i++)
174 if (supported_gss_krb5_enctypes[i].etype == etype)
180 get_gss_krb5_enctype(
int etype)
183 for (i = 0; i < num_supported_enctypes; i++)
184 if (supported_gss_krb5_enctypes[i].etype == etype)
185 return &supported_gss_krb5_enctypes[
i];
190 simple_get_bytes(
const void *
p,
const void *
end,
void *
res,
int len)
192 const void *
q = (
const void *)((
const char *)p + len);
200 simple_get_netobj(
const void *p,
const void *end,
struct xdr_netobj *res)
205 p = simple_get_bytes(p, end, &len,
sizeof(len));
208 q = (
const void *)((
const char *)p + len);
218 static inline const void *
219 get_key(
const void *p,
const void *end,
222 struct xdr_netobj
key;
225 p = simple_get_bytes(p, end, &alg,
sizeof(alg));
238 if (!supported_gss_krb5_enctype(alg)) {
240 "encryption key algorithm %d\n", alg);
244 p = simple_get_netobj(p, end, &
key);
248 *res = crypto_alloc_blkcipher(ctx->
gk5e->encrypt_name, 0,
252 "crypto algorithm %s\n", ctx->
gk5e->encrypt_name);
254 goto out_err_free_key;
256 if (crypto_blkcipher_setkey(*res,
key.data,
key.len)) {
258 "crypto algorithm %s\n", ctx->
gk5e->encrypt_name);
259 goto out_err_free_tfm;
266 crypto_free_blkcipher(*res);
275 gss_import_v1_context(
const void *p,
const void *end,
struct krb5_ctx *ctx)
296 if (
unlikely(p + 20 > end || p + 20 < p)) {
301 p = simple_get_bytes(p, end, &tmp,
sizeof(tmp));
308 p = simple_get_bytes(p, end, &tmp,
sizeof(tmp));
315 p = simple_get_bytes(p, end, &ctx->
endtime,
sizeof(ctx->
endtime));
321 p = simple_get_netobj(p, end, &ctx->
mech_used);
324 p = get_key(p, end, ctx, &ctx->
enc);
326 goto out_err_free_mech;
327 p = get_key(p, end, ctx, &ctx->
seq);
329 goto out_err_free_key1;
332 goto out_err_free_key2;
338 crypto_free_blkcipher(ctx->
seq);
340 crypto_free_blkcipher(ctx->
enc);
354 dprintk(
"gss_kerberos_mech: unable to initialize "
355 "crypto algorithm %s\n", cname);
358 if (crypto_blkcipher_setkey(cp, key, ctx->
gk5e->keylength)) {
359 dprintk(
"gss_kerberos_mech: error setting key for "
360 "crypto algorithm %s\n", cname);
361 crypto_free_blkcipher(cp);
370 cdata[0] = (usage>>24)&0xff;
371 cdata[1] = (usage>>16)&0xff;
372 cdata[2] = (usage>>8)&0xff;
373 cdata[3] = usage&0xff;
392 ctx->
seq = context_v2_alloc_cipher(ctx, ctx->
gk5e->encrypt_name,
397 ctx->
enc = context_v2_alloc_cipher(ctx, ctx->
gk5e->encrypt_name,
407 dprintk(
"%s: Error %d deriving cksum key\n",
415 crypto_free_blkcipher(ctx->
enc);
417 crypto_free_blkcipher(ctx->
seq);
428 context_derive_keys_rc4(
struct krb5_ctx *ctx)
431 char sigkeyconstant[] =
"signaturekey";
432 int slen =
strlen(sigkeyconstant) + 1;
437 dprintk(
"RPC: %s: entered\n", __func__);
443 dprintk(
"%s: error %ld allocating hash '%s'\n",
444 __func__, PTR_ERR(hmac), ctx->
gk5e->cksum_name);
449 err = crypto_hash_setkey(hmac, ctx->
Ksess, ctx->
gk5e->keylength);
451 goto out_err_free_hmac;
454 sg_set_buf(
sg, sigkeyconstant, slen);
459 err = crypto_hash_init(&
desc);
461 goto out_err_free_hmac;
463 err = crypto_hash_digest(&
desc,
sg, slen, ctx->
cksum);
465 goto out_err_free_hmac;
469 ctx->
enc = crypto_alloc_blkcipher(ctx->
gk5e->encrypt_name, 0,
471 if (IS_ERR(ctx->
enc)) {
472 err = PTR_ERR(ctx->
enc);
473 goto out_err_free_hmac;
476 ctx->
seq = crypto_alloc_blkcipher(ctx->
gk5e->encrypt_name, 0,
478 if (IS_ERR(ctx->
seq)) {
479 crypto_free_blkcipher(ctx->
enc);
480 err = PTR_ERR(ctx->
seq);
481 goto out_err_free_hmac;
484 dprintk(
"RPC: %s: returning success\n", __func__);
489 crypto_free_hash(hmac);
491 dprintk(
"RPC: %s: returning %d\n", __func__, err);
496 context_derive_keys_new(
struct krb5_ctx *ctx,
gfp_t gfp_mask)
514 dprintk(
"%s: Error %d deriving initiator_seal key\n",
519 ctx->
gk5e->encrypt_name,
529 dprintk(
"%s: Error %d deriving acceptor_seal key\n",
531 goto out_free_initiator_enc;
534 ctx->
gk5e->encrypt_name,
537 goto out_free_initiator_enc;
544 dprintk(
"%s: Error %d deriving initiator_sign key\n",
546 goto out_free_acceptor_enc;
554 dprintk(
"%s: Error %d deriving acceptor_sign key\n",
556 goto out_free_acceptor_enc;
564 dprintk(
"%s: Error %d deriving initiator_integ key\n",
566 goto out_free_acceptor_enc;
574 dprintk(
"%s: Error %d deriving acceptor_integ key\n",
576 goto out_free_acceptor_enc;
583 context_v2_alloc_cipher(ctx,
"cbc(aes)",
586 goto out_free_acceptor_enc;
588 context_v2_alloc_cipher(ctx,
"cbc(aes)",
592 goto out_free_acceptor_enc;
598 out_free_acceptor_enc:
600 out_free_initiator_enc:
607 gss_import_v2_context(
const void *p,
const void *end,
struct krb5_ctx *ctx,
612 p = simple_get_bytes(p, end, &ctx->
flags,
sizeof(ctx->
flags));
617 p = simple_get_bytes(p, end, &ctx->
endtime,
sizeof(ctx->
endtime));
626 dprintk(
"%s: seq_send64 %lx, seq_send %x overflow?\n", __func__,
631 p = simple_get_bytes(p, end, &ctx->
enctype,
sizeof(ctx->
enctype));
639 dprintk(
"gss_kerberos_mech: unsupported krb5 enctype %u\n",
644 keylen = ctx->
gk5e->keylength;
646 p = simple_get_bytes(p, end, ctx->
Ksess, keylen);
656 gss_kerberos_mech.gm_oid.len, gfp_mask);
661 ctx->
mech_used.len = gss_kerberos_mech.gm_oid.len;
665 return context_derive_keys_des3(ctx, gfp_mask);
667 return context_derive_keys_rc4(ctx);
670 return context_derive_keys_new(ctx, gfp_mask);
680 gss_import_sec_context_kerberos(
const void *p,
size_t len,
684 const void *end = (
const void *)((
const char *)p + len);
688 ctx = kzalloc(
sizeof(*ctx), gfp_mask);
693 ret = gss_import_v1_context(p, end, ctx);
695 ret = gss_import_v2_context(p, end, ctx, gfp_mask);
698 ctx_id->internal_ctx_id =
ctx;
702 dprintk(
"RPC: %s: returning %d\n", __func__, ret);
707 gss_delete_sec_context_kerberos(
void *internal_ctx) {
708 struct krb5_ctx *kctx = internal_ctx;
710 crypto_free_blkcipher(kctx->
seq);
711 crypto_free_blkcipher(kctx->
enc);
720 static const struct gss_api_ops gss_kerberos_ops = {
721 .gss_import_sec_context = gss_import_sec_context_kerberos,
726 .gss_delete_sec_context = gss_delete_sec_context_kerberos,
729 static struct pf_desc gss_kerberos_pfs[] = {
731 .pseudoflavor = RPC_AUTH_GSS_KRB5,
732 .service = RPC_GSS_SVC_NONE,
736 .pseudoflavor = RPC_AUTH_GSS_KRB5I,
737 .service = RPC_GSS_SVC_INTEGRITY,
741 .pseudoflavor = RPC_AUTH_GSS_KRB5P,
742 .service = RPC_GSS_SVC_PRIVACY,
754 static struct gss_api_mech gss_kerberos_mech = {
757 .gm_oid = {9, (
void *)
"\x2a\x86\x48\x86\xf7\x12\x01\x02\x02"},
758 .gm_ops = &gss_kerberos_ops,
760 .gm_pfs = gss_kerberos_pfs,
764 static int __init init_kerberos_module(
void)
770 printk(
"Failed to register kerberos gss mechanism!\n");
774 static void __exit cleanup_kerberos_module(
void)