diff options
author | william <william+macosx@25thandclement.com> | 2015-06-04 15:26:30 -0700 |
---|---|---|
committer | william <william+macosx@25thandclement.com> | 2015-06-04 15:26:30 -0700 |
commit | dc6063ab7dcc99462dcca0bcaa92a00dbf5c3fcb (patch) | |
tree | 0a46e3a7a7fbfdc9a0c00d26e7e52548bef3b569 | |
parent | f9ad758d661f8f288e11f7071a05fa3d7d64ff27 (diff) | |
download | luaossl-dc6063ab7dcc99462dcca0bcaa92a00dbf5c3fcb.tar.gz luaossl-dc6063ab7dcc99462dcca0bcaa92a00dbf5c3fcb.tar.bz2 luaossl-dc6063ab7dcc99462dcca0bcaa92a00dbf5c3fcb.zip |
add extension:getID, extension:getName, extension:getShortName, extension:getLongName, extension:getCritical, and crl:getExtension
-rw-r--r-- | src/openssl.c | 253 |
1 files changed, 220 insertions, 33 deletions
diff --git a/src/openssl.c b/src/openssl.c index 629373d..a4efcdc 100644 --- a/src/openssl.c +++ b/src/openssl.c | |||
@@ -460,32 +460,25 @@ static void *loadfield_udata(lua_State *L, int index, const char *k, const char | |||
460 | } /* loadfield_udata() */ | 460 | } /* loadfield_udata() */ |
461 | 461 | ||
462 | 462 | ||
463 | static const char *pushnid(lua_State *L, int nid) { | 463 | /* |
464 | const char *txt; | 464 | * Auxiliary C routines |
465 | ASN1_OBJECT *obj; | 465 | * |
466 | char buf[256]; | 466 | * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ |
467 | int len; | ||
468 | |||
469 | if ((txt = OBJ_nid2sn(nid)) || (txt = OBJ_nid2ln(nid))) { | ||
470 | lua_pushstring(L, txt); | ||
471 | } else { | ||
472 | if (!(obj = OBJ_nid2obj(nid))) | ||
473 | luaL_error(L, "%d: unknown ASN.1 NID", nid); | ||
474 | 467 | ||
475 | if (-1 == (len = OBJ_obj2txt(buf, sizeof buf, obj, 1))) | 468 | #define AUX_MIN(a, b) (((a) < (b))? (a) : (b)) |
476 | luaL_error(L, "%d: invalid ASN.1 NID", nid); | ||
477 | 469 | ||
478 | lua_pushlstring(L, buf, len); | 470 | static size_t aux_strlcpy(char *dst, const char *src, size_t lim) { |
479 | } | 471 | size_t n = strlen(src); |
480 | 472 | ||
481 | return lua_tostring(L, -1); | 473 | if (lim > 0) { |
482 | } /* pushnid() */ | 474 | size_t m = AUX_MIN(lim - 1, n); |
483 | 475 | ||
476 | memcpy(dst, src, m); | ||
477 | dst[m] = '\0'; | ||
478 | } | ||
484 | 479 | ||
485 | /* | 480 | return n; |
486 | * Auxiliary C routines | 481 | } /* aux_strlcpy() */ |
487 | * | ||
488 | * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ | ||
489 | 482 | ||
490 | #define aux_strerror(error) aux_strerror_r((error), (char[256]){ 0 }, 256) | 483 | #define aux_strerror(error) aux_strerror_r((error), (char[256]){ 0 }, 256) |
491 | 484 | ||
@@ -517,6 +510,83 @@ static const char *aux_strerror_r(int error, char *dst, size_t lim) { | |||
517 | 510 | ||
518 | 511 | ||
519 | /* | 512 | /* |
513 | * Auxiliary OpenSSL API routines | ||
514 | * | ||
515 | * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ | ||
516 | |||
517 | static size_t auxS_nid2sn(void *dst, size_t lim, int nid) { | ||
518 | const char *sn; | ||
519 | |||
520 | if (nid == NID_undef || !(sn = OBJ_nid2sn(nid))) | ||
521 | return 0; | ||
522 | |||
523 | return aux_strlcpy(dst, sn, lim); | ||
524 | } /* aux2_nid2sn() */ | ||
525 | |||
526 | static size_t auxS_obj2sn(void *dst, size_t lim, const ASN1_OBJECT *obj) { | ||
527 | return auxS_nid2sn(dst, lim, OBJ_obj2nid(obj)); | ||
528 | } /* auxS_obj2sn() */ | ||
529 | |||
530 | static size_t auxS_nid2ln(void *dst, size_t lim, int nid) { | ||
531 | const char *ln; | ||
532 | |||
533 | if (nid == NID_undef || !(ln = OBJ_nid2ln(nid))) | ||
534 | return 0; | ||
535 | |||
536 | return aux_strlcpy(dst, ln, lim); | ||
537 | } /* aux2_nid2ln() */ | ||
538 | |||
539 | static size_t auxS_obj2ln(void *dst, size_t lim, const ASN1_OBJECT *obj) { | ||
540 | return auxS_nid2ln(dst, lim, OBJ_obj2nid(obj)); | ||
541 | } /* auxS_obj2ln() */ | ||
542 | |||
543 | static size_t auxS_obj2id(void *dst, size_t lim, const ASN1_OBJECT *obj) { | ||
544 | int n = OBJ_obj2txt(dst, AUX_MIN(lim, INT_MAX), obj, 1); | ||
545 | |||
546 | /* TODO: push custom errors onto error stack */ | ||
547 | if (n == 0) { | ||
548 | return 0; /* obj->data == NULL */ | ||
549 | } else if (n < 0) { | ||
550 | return 0; /* memory allocation error */ | ||
551 | } else { | ||
552 | return n; | ||
553 | } | ||
554 | } /* auxS_obj2id() */ | ||
555 | |||
556 | static size_t auxS_nid2id(void *dst, size_t lim, int nid) { | ||
557 | ASN1_OBJECT *obj; | ||
558 | |||
559 | /* TODO: push custom error onto error stack */ | ||
560 | if (!(obj = OBJ_nid2obj(nid))) | ||
561 | return 0; | ||
562 | |||
563 | return auxS_obj2id(dst, lim, obj); | ||
564 | } /* auxS_nid2id() */ | ||
565 | |||
566 | static size_t auxS_nid2txt(void *dst, size_t lim, int nid) { | ||
567 | size_t n; | ||
568 | |||
569 | if ((n = auxS_nid2sn(dst, lim, nid))) | ||
570 | return n; | ||
571 | if ((n = auxS_nid2ln(dst, lim, nid))) | ||
572 | return n; | ||
573 | |||
574 | return auxS_nid2id(dst, lim, nid); | ||
575 | } /* auxS_nid2txt() */ | ||
576 | |||
577 | static size_t auxS_obj2txt(void *dst, size_t lim, const ASN1_OBJECT *obj) { | ||
578 | size_t n; | ||
579 | |||
580 | if ((n = auxS_obj2sn(dst, lim, obj))) | ||
581 | return n; | ||
582 | if ((n = auxS_obj2ln(dst, lim, obj))) | ||
583 | return n; | ||
584 | |||
585 | return auxS_obj2id(dst, lim, obj); | ||
586 | } /* auxS_obj2txt() */ | ||
587 | |||
588 | |||
589 | /* | ||
520 | * Auxiliary Lua API routines | 590 | * Auxiliary Lua API routines |
521 | * | 591 | * |
522 | * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ | 592 | * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ |
@@ -685,6 +755,18 @@ static int auxL_error(lua_State *L, int error, const char *fun) { | |||
685 | return lua_error(L); | 755 | return lua_error(L); |
686 | } /* auxL_error() */ | 756 | } /* auxL_error() */ |
687 | 757 | ||
758 | static const char *auxL_pushnid(lua_State *L, int nid) { | ||
759 | char txt[256] = { 0 }; | ||
760 | size_t n; | ||
761 | |||
762 | if (!(n = auxS_nid2txt(txt, sizeof txt, nid)) || n >= sizeof txt) | ||
763 | luaL_error(L, "%d: invalid ASN.1 NID", nid); | ||
764 | |||
765 | lua_pushlstring(L, txt, n); | ||
766 | |||
767 | return lua_tostring(L, -1); | ||
768 | } /* auxL_pushnid() */ | ||
769 | |||
688 | 770 | ||
689 | /* | 771 | /* |
690 | * dl - dynamically loaded module management | 772 | * dl - dynamically loaded module management |
@@ -796,6 +878,14 @@ static void *compat_EVP_PKEY_get0(EVP_PKEY *key) { | |||
796 | #define X509_get0_ext(crt, i) X509_get_ext((crt), (i)) | 878 | #define X509_get0_ext(crt, i) X509_get_ext((crt), (i)) |
797 | #endif | 879 | #endif |
798 | 880 | ||
881 | #if !HAVE_X509_CRL_GET0_EXT | ||
882 | #define X509_CRL_get0_ext(crt, i) X509_CRL_get_ext((crt), (i)) | ||
883 | #endif | ||
884 | |||
885 | #if !HAVE_X509_EXTENSION_GET0_OBJECT | ||
886 | #define X509_EXTENSION_get0_object(ext) X509_EXTENSION_get_object((ext)) | ||
887 | #endif | ||
888 | |||
799 | #if !HAVE_X509_EXTENSION_GET0_DATA | 889 | #if !HAVE_X509_EXTENSION_GET0_DATA |
800 | #define X509_EXTENSION_get0_data(ext) X509_EXTENSION_get_data((ext)) | 890 | #define X509_EXTENSION_get0_data(ext) X509_EXTENSION_get_data((ext)) |
801 | #endif | 891 | #endif |
@@ -2103,7 +2193,7 @@ static int pk_type(lua_State *L) { | |||
2103 | EVP_PKEY *key = checksimple(L, 1, PKEY_CLASS); | 2193 | EVP_PKEY *key = checksimple(L, 1, PKEY_CLASS); |
2104 | int nid = key->type; | 2194 | int nid = key->type; |
2105 | 2195 | ||
2106 | pushnid(L, nid); | 2196 | auxL_pushnid(L, nid); |
2107 | 2197 | ||
2108 | return 1; | 2198 | return 1; |
2109 | } /* pk_type() */ | 2199 | } /* pk_type() */ |
@@ -2526,16 +2616,10 @@ static int xn__next(lua_State *L) { | |||
2526 | continue; | 2616 | continue; |
2527 | 2617 | ||
2528 | obj = X509_NAME_ENTRY_get_object(entry); | 2618 | obj = X509_NAME_ENTRY_get_object(entry); |
2529 | nid = OBJ_obj2nid(obj); | ||
2530 | |||
2531 | if (nid != NID_undef && ((id = OBJ_nid2sn(nid)) || (id = OBJ_nid2ln(nid)))) { | ||
2532 | lua_pushstring(L, id); | ||
2533 | } else { | ||
2534 | if (0 > (len = OBJ_obj2txt(txt, sizeof txt, obj, 1))) | ||
2535 | return auxL_error(L, auxL_EOPENSSL, "x509.name:__pairs"); | ||
2536 | 2619 | ||
2537 | lua_pushlstring(L, txt, len); | 2620 | if (!(len = auxS_obj2txt(txt, sizeof txt, obj))) |
2538 | } | 2621 | return auxL_error(L, auxL_EOPENSSL, "x509.name:__pairs"); |
2622 | lua_pushlstring(L, txt, len); | ||
2539 | 2623 | ||
2540 | len = ASN1_STRING_length(X509_NAME_ENTRY_get_data(entry)); | 2624 | len = ASN1_STRING_length(X509_NAME_ENTRY_get_data(entry)); |
2541 | lua_pushlstring(L, (char *)ASN1_STRING_data(X509_NAME_ENTRY_get_data(entry)), len); | 2625 | lua_pushlstring(L, (char *)ASN1_STRING_data(X509_NAME_ENTRY_get_data(entry)), len); |
@@ -2960,6 +3044,63 @@ static int xe_interpose(lua_State *L) { | |||
2960 | } /* xe_interpose() */ | 3044 | } /* xe_interpose() */ |
2961 | 3045 | ||
2962 | 3046 | ||
3047 | static int xe_getID(lua_State *L) { | ||
3048 | X509_EXTENSION *ext = checksimple(L, 1, X509_EXT_CLASS); | ||
3049 | ASN1_OBJECT *obj = X509_EXTENSION_get0_object(ext); | ||
3050 | char txt[256]; | ||
3051 | int len; | ||
3052 | |||
3053 | if (!(len = auxS_obj2id(txt, sizeof txt, obj))) | ||
3054 | return auxL_error(L, auxL_EOPENSSL, "x509.extension:getID"); | ||
3055 | |||
3056 | lua_pushlstring(L, txt, len); | ||
3057 | |||
3058 | return 1; | ||
3059 | } /* xe_getID() */ | ||
3060 | |||
3061 | |||
3062 | static int xe_getName(lua_State *L) { | ||
3063 | X509_EXTENSION *ext = checksimple(L, 1, X509_EXT_CLASS); | ||
3064 | char txt[256]; | ||
3065 | int len; | ||
3066 | |||
3067 | if (!(len = auxS_obj2txt(txt, sizeof txt, X509_EXTENSION_get0_object(ext)))) | ||
3068 | return auxL_error(L, auxL_EOPENSSL, "x509.extension:getName"); | ||
3069 | |||
3070 | lua_pushlstring(L, txt, len); | ||
3071 | |||
3072 | return 1; | ||
3073 | } /* xe_getName() */ | ||
3074 | |||
3075 | |||
3076 | static int xe_getShortName(lua_State *L) { | ||
3077 | X509_EXTENSION *ext = checksimple(L, 1, X509_EXT_CLASS); | ||
3078 | char txt[256]; | ||
3079 | int len; | ||
3080 | |||
3081 | if (!(len = auxS_obj2sn(txt, sizeof txt, X509_EXTENSION_get0_object(ext)))) | ||
3082 | return 0; | ||
3083 | |||
3084 | lua_pushlstring(L, txt, len); | ||
3085 | |||
3086 | return 1; | ||
3087 | } /* xe_getShortName() */ | ||
3088 | |||
3089 | |||
3090 | static int xe_getLongName(lua_State *L) { | ||
3091 | X509_EXTENSION *ext = checksimple(L, 1, X509_EXT_CLASS); | ||
3092 | char txt[256]; | ||
3093 | int len; | ||
3094 | |||
3095 | if (!(len = auxS_obj2ln(txt, sizeof txt, X509_EXTENSION_get0_object(ext)))) | ||
3096 | return 0; | ||
3097 | |||
3098 | lua_pushlstring(L, txt, len); | ||
3099 | |||
3100 | return 1; | ||
3101 | } /* xe_getLongName() */ | ||
3102 | |||
3103 | |||
2963 | static int xe_getData(lua_State *L) { | 3104 | static int xe_getData(lua_State *L) { |
2964 | ASN1_STRING *data = X509_EXTENSION_get0_data(checksimple(L, 1, X509_EXT_CLASS)); | 3105 | ASN1_STRING *data = X509_EXTENSION_get0_data(checksimple(L, 1, X509_EXT_CLASS)); |
2965 | 3106 | ||
@@ -2969,6 +3110,13 @@ static int xe_getData(lua_State *L) { | |||
2969 | } /* xe_getData() */ | 3110 | } /* xe_getData() */ |
2970 | 3111 | ||
2971 | 3112 | ||
3113 | static int xe_getCritical(lua_State *L) { | ||
3114 | lua_pushboolean(L, X509_EXTENSION_get_critical(checksimple(L, 1, X509_EXT_CLASS))); | ||
3115 | |||
3116 | return 1; | ||
3117 | } /* xe_getCritical() */ | ||
3118 | |||
3119 | |||
2972 | static int xe__gc(lua_State *L) { | 3120 | static int xe__gc(lua_State *L) { |
2973 | X509_EXTENSION **ud = luaL_checkudata(L, 1, X509_EXT_CLASS); | 3121 | X509_EXTENSION **ud = luaL_checkudata(L, 1, X509_EXT_CLASS); |
2974 | 3122 | ||
@@ -2982,8 +3130,13 @@ static int xe__gc(lua_State *L) { | |||
2982 | 3130 | ||
2983 | 3131 | ||
2984 | static const luaL_Reg xe_methods[] = { | 3132 | static const luaL_Reg xe_methods[] = { |
2985 | { "getData", &xe_getData }, | 3133 | { "getID", &xe_getID }, |
2986 | { NULL, NULL }, | 3134 | { "getName", &xe_getName }, |
3135 | { "getShortName", &xe_getShortName }, | ||
3136 | { "getLongName", &xe_getLongName }, | ||
3137 | { "getData", &xe_getData }, | ||
3138 | { "getCritical", &xe_getCritical }, | ||
3139 | { NULL, NULL }, | ||
2987 | }; | 3140 | }; |
2988 | 3141 | ||
2989 | static const luaL_Reg xe_metatable[] = { | 3142 | static const luaL_Reg xe_metatable[] = { |
@@ -3702,6 +3855,7 @@ static int xc_addExtension(lua_State *L) { | |||
3702 | X509 *crt = checksimple(L, 1, X509_CERT_CLASS); | 3855 | X509 *crt = checksimple(L, 1, X509_CERT_CLASS); |
3703 | X509_EXTENSION *ext = checksimple(L, 2, X509_EXT_CLASS); | 3856 | X509_EXTENSION *ext = checksimple(L, 2, X509_EXT_CLASS); |
3704 | 3857 | ||
3858 | /* NOTE: Will dup extension in X509v3_add_ext. */ | ||
3705 | if (!X509_add_ext(crt, ext, -1)) | 3859 | if (!X509_add_ext(crt, ext, -1)) |
3706 | return auxL_error(L, auxL_EOPENSSL, "x509.cert:addExtension"); | 3860 | return auxL_error(L, auxL_EOPENSSL, "x509.cert:addExtension"); |
3707 | 3861 | ||
@@ -4461,6 +4615,38 @@ static int xx_addExtension(lua_State *L) { | |||
4461 | return 1; | 4615 | return 1; |
4462 | } /* xx_addExtension() */ | 4616 | } /* xx_addExtension() */ |
4463 | 4617 | ||
4618 | |||
4619 | static int xx_getExtension(lua_State *L) { | ||
4620 | X509_CRL *crl = checksimple(L, 1, X509_CRL_CLASS); | ||
4621 | const char *name = luaL_checkstring(L, 2); | ||
4622 | X509_EXTENSION *ext, **ud; | ||
4623 | ASN1_OBJECT *obj = NULL; | ||
4624 | |||
4625 | if (!(obj = OBJ_txt2obj(name, 0))) | ||
4626 | goto error; | ||
4627 | |||
4628 | int i = X509_CRL_get_ext_by_OBJ(crl, obj, -1); | ||
4629 | if (i > -1) { | ||
4630 | ud = prepsimple(L, X509_CRL_CLASS); | ||
4631 | if (!(ext = X509_CRL_get0_ext(crl, i))) | ||
4632 | goto error; | ||
4633 | if (!(*ud = X509_EXTENSION_dup(ext))) | ||
4634 | goto error; | ||
4635 | } else { | ||
4636 | lua_pushnil(L); | ||
4637 | } | ||
4638 | |||
4639 | ASN1_OBJECT_free(obj); | ||
4640 | |||
4641 | return 1; | ||
4642 | error: | ||
4643 | if (obj) | ||
4644 | ASN1_OBJECT_free(obj); | ||
4645 | |||
4646 | return auxL_error(L, auxL_EOPENSSL, "x509.crl:getExtension"); | ||
4647 | } /* xx_getExtension() */ | ||
4648 | |||
4649 | |||
4464 | static int xx_sign(lua_State *L) { | 4650 | static int xx_sign(lua_State *L) { |
4465 | X509_CRL *crl = checksimple(L, 1, X509_CRL_CLASS); | 4651 | X509_CRL *crl = checksimple(L, 1, X509_CRL_CLASS); |
4466 | EVP_PKEY *key = checksimple(L, 2, PKEY_CLASS); | 4652 | EVP_PKEY *key = checksimple(L, 2, PKEY_CLASS); |
@@ -4540,6 +4726,7 @@ static const luaL_Reg xx_methods[] = { | |||
4540 | { "setIssuer", &xx_setIssuer }, | 4726 | { "setIssuer", &xx_setIssuer }, |
4541 | { "add", &xx_add }, | 4727 | { "add", &xx_add }, |
4542 | { "addExtension", &xx_addExtension }, | 4728 | { "addExtension", &xx_addExtension }, |
4729 | { "getExtension", &xx_getExtension }, | ||
4543 | { "sign", &xx_sign }, | 4730 | { "sign", &xx_sign }, |
4544 | { "text", &xx_text }, | 4731 | { "text", &xx_text }, |
4545 | { "tostring", &xx__tostring }, | 4732 | { "tostring", &xx__tostring }, |