tl;dr: Can anyone with Cisco equipment with AES-192 and AES-256 support
for snmp test the diff below as much -a variants as possible and report
back to me?

According to the archives there was once an initiative for AES-192 and
AES-256[0]. Unfortunately this was removed after draft 4.

Since version 5.8 Net-SNMP has support for this draft[1], but the key
expansion[2] is based around draft-reeder-snmpv3-usm-3desede-00[3].
To try AES-192 and AES-256 on net-snmp it must be compiled with
--enable-blumenthal-aes, which we currently don't do.
Unfortunately I haven't even been able to get this to work with
anything other than SHA-512 + AES-256 even between net-snmp as daemon
and cli client, so the key expansion remains untested.

Any help is welcome.

martijn@

[0] https://tools.ietf.org/html/draft-blumenthal-aes-usm-04
[1] https://sourceforge.net/p/net-snmp/code/ci/master/tree/NEWS
[2] 
https://sourceforge.net/p/net-snmp/code/ci/9e49de2e03b18ceb1b7cba2e715ad6180f394815/log/?path=
[3] http://www.snmp.com/eso/draft-reeder-snmpv3-usm-3desede-00.txt

Index: snmp.1
===================================================================
RCS file: /cvs/src/usr.bin/snmp/snmp.1,v
retrieving revision 1.8
diff -u -p -r1.8 snmp.1
--- snmp.1      26 Oct 2019 17:43:52 -0000      1.8
+++ snmp.1      28 Oct 2019 10:52:27 -0000
@@ -399,9 +399,11 @@ Sets the cipher
 .Pq privacy
 protocol.
 Options are
-.Cm DES
+.Cm DES ,
+.Cm AES ,
+.Cm AES-192
 and
-.Cm AES .
+.Cm AES-256 .
 This option is only used by
 .Fl v Cm 3 .
 .It Fl Z Ar boots , Ns Ar time
Index: snmpc.c
===================================================================
RCS file: /cvs/src/usr.bin/snmp/snmpc.c,v
retrieving revision 1.17
diff -u -p -r1.17 snmpc.c
--- snmpc.c     26 Oct 2019 19:34:15 -0000      1.17
+++ snmpc.c     28 Oct 2019 10:52:27 -0000
@@ -401,6 +401,12 @@ main(int argc, char *argv[])
                                cipher = EVP_des_cbc();
                        else if (strcasecmp(optarg, "AES") == 0)
                                cipher = EVP_aes_128_cfb128();
+                       else if (strcasecmp(optarg, "AES-192") == 0 ||
+                           strcasecmp(optarg, "AES192") == 0)
+                               cipher = EVP_aes_192_cfb128();
+                       else if (strcasecmp(optarg, "AES-256") == 0 ||
+                           strcasecmp(optarg, "AES256") == 0)
+                               cipher = EVP_aes_256_cfb128();
                        else
                                errx(1, "Invalid privacy protocol "
                                    "specified after -3x flag: %s",
Index: usm.c
===================================================================
RCS file: /cvs/src/usr.bin/snmp/usm.c,v
retrieving revision 1.5
diff -u -p -r1.5 usm.c
--- usm.c       24 Oct 2019 12:39:26 -0000      1.5
+++ usm.c       28 Oct 2019 10:52:27 -0000
@@ -267,6 +267,8 @@ usm_crypt(const EVP_CIPHER *cipher, int 
                        iv[i] = salt[i] ^ key[USM_SALTOFFSET + i];
                break;
        case NID_aes_128_cfb128:
+       case NID_aes_192_cfb128:
+       case NID_aes_256_cfb128:
                /* RFC3826, chap 3.1.2.1. */
                ivv = htobe32(cookie->boots);
                memcpy(iv, &ivv, sizeof(ivv));
@@ -650,8 +652,10 @@ usm_mkey2lkey(struct usm_sec *usm, const
 {
        EVP_MD_CTX ctx;
        u_char buf[EVP_MAX_MD_SIZE];
-       u_char *lkey;
-       unsigned lklen;
+       u_char *lkey, *tlkey;
+       unsigned hlen;
+       int keylen;
+       size_t lklen;
 
        bzero(&ctx, sizeof(ctx));
        EVP_DigestInit_ex(&ctx, md, NULL);
@@ -660,12 +664,28 @@ usm_mkey2lkey(struct usm_sec *usm, const
        EVP_DigestUpdate(&ctx, usm->engineid, usm->engineidlen);
        EVP_DigestUpdate(&ctx, mkey, EVP_MD_size(md));
 
-       EVP_DigestFinal_ex(&ctx, buf, &lklen);
+       EVP_DigestFinal_ex(&ctx, buf, &hlen);
        EVP_MD_CTX_cleanup(&ctx);
 
-       if ((lkey = malloc(lklen)) == NULL)
+       if ((lkey = malloc(hlen)) == NULL)
                return NULL;
-       memcpy(lkey, buf, lklen);
+       memcpy(lkey, buf, hlen);
+       lklen = hlen;
+
+       for (keylen = EVP_CIPHER_key_length(usm->cipher) - hlen; keylen > 0;
+           keylen -= hlen) {
+               EVP_DigestInit_ex(&ctx, md, NULL);
+               EVP_DigestUpdate(&ctx, buf, lklen);
+               EVP_DigestUpdate(&ctx, usm->engineid, usm->engineidlen);
+               EVP_DigestFinal_ex(&ctx, buf, &hlen);
+               if ((tlkey = realloc(lkey, lklen + hlen)) == NULL) {
+                       free(lkey);
+                       return NULL;
+               }
+               lkey = tlkey;
+               memcpy(lkey + lklen, buf, hlen);
+               lklen += hlen;
+       }
        return lkey;
 }
 

Reply via email to