New upstream version 22.0.3+dfsg1
This commit is contained in:
parent
665f64a933
commit
cdc9a9fc87
334 changed files with 14525 additions and 2639 deletions
|
|
@ -29,6 +29,7 @@
|
|||
#include "bytes.h"
|
||||
|
||||
static const AMFObjectProperty AMFProp_Invalid = { {0, 0}, AMF_INVALID };
|
||||
static const AMFObject AMFObj_Invalid = { 0, 0 };
|
||||
static const AVal AV_empty = { 0, 0 };
|
||||
|
||||
/* Data is Big-Endian */
|
||||
|
|
@ -336,13 +337,19 @@ AMFProp_GetBoolean(AMFObjectProperty *prop)
|
|||
void
|
||||
AMFProp_GetString(AMFObjectProperty *prop, AVal *str)
|
||||
{
|
||||
*str = prop->p_vu.p_aval;
|
||||
if (prop->p_type == AMF_STRING)
|
||||
*str = prop->p_vu.p_aval;
|
||||
else
|
||||
*str = AV_empty;
|
||||
}
|
||||
|
||||
void
|
||||
AMFProp_GetObject(AMFObjectProperty *prop, AMFObject *obj)
|
||||
{
|
||||
*obj = prop->p_vu.p_object;
|
||||
if (prop->p_type == AMF_OBJECT)
|
||||
*obj = prop->p_vu.p_object;
|
||||
else
|
||||
*obj = AMFObj_Invalid;
|
||||
}
|
||||
|
||||
int
|
||||
|
|
@ -472,6 +479,8 @@ AMF3ReadString(const char *data, AVal *str)
|
|||
RTMP_Log(RTMP_LOGDEBUG,
|
||||
"%s, string reference, index: %d, not supported, ignoring!",
|
||||
__FUNCTION__, refIndex);
|
||||
str->av_val = NULL;
|
||||
str->av_len = 0;
|
||||
return len;
|
||||
}
|
||||
else
|
||||
|
|
@ -511,9 +520,12 @@ AMF3Prop_Decode(AMFObjectProperty *prop, const char *pBuffer, int nSize,
|
|||
if (name.av_len <= 0)
|
||||
return nRes;
|
||||
|
||||
nSize -= nRes;
|
||||
if (nSize <= 0)
|
||||
return -1;
|
||||
|
||||
prop->p_name = name;
|
||||
pBuffer += nRes;
|
||||
nSize -= nRes;
|
||||
}
|
||||
|
||||
/* decode */
|
||||
|
|
@ -601,6 +613,9 @@ AMF3Prop_Decode(AMFObjectProperty *prop, const char *pBuffer, int nSize,
|
|||
return -1;
|
||||
}
|
||||
|
||||
if (nSize < 0)
|
||||
return -1;
|
||||
|
||||
return nOriginalSize - nSize;
|
||||
}
|
||||
|
||||
|
|
@ -994,9 +1009,18 @@ AMF_DecodeArray(AMFObject *obj, const char *pBuffer, int nSize,
|
|||
int nRes;
|
||||
nArrayLen--;
|
||||
|
||||
if (nSize <= 0)
|
||||
{
|
||||
bError = TRUE;
|
||||
break;
|
||||
}
|
||||
|
||||
nRes = AMFProp_Decode(&prop, pBuffer, nSize, bDecodeName);
|
||||
if (nRes == -1)
|
||||
{
|
||||
bError = TRUE;
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
nSize -= nRes;
|
||||
|
|
@ -1057,12 +1081,12 @@ AMF3_Decode(AMFObject *obj, const char *pBuffer, int nSize, int bAMFData)
|
|||
else
|
||||
{
|
||||
int32_t classExtRef = (classRef >> 1);
|
||||
int i;
|
||||
int i, cdnum;
|
||||
|
||||
cd.cd_externalizable = (classExtRef & 0x1) == 1;
|
||||
cd.cd_dynamic = ((classExtRef >> 1) & 0x1) == 1;
|
||||
|
||||
cd.cd_num = classExtRef >> 2;
|
||||
cdnum = classExtRef >> 2;
|
||||
|
||||
/* class name */
|
||||
|
||||
|
|
@ -1077,9 +1101,16 @@ AMF3_Decode(AMFObject *obj, const char *pBuffer, int nSize, int bAMFData)
|
|||
cd.cd_name.av_val, cd.cd_externalizable, cd.cd_dynamic,
|
||||
cd.cd_num);
|
||||
|
||||
for (i = 0; i < cd.cd_num; i++)
|
||||
for (i = 0; i < cdnum; i++)
|
||||
{
|
||||
AVal memberName = AV_empty;
|
||||
if (nSize <= 0)
|
||||
{
|
||||
invalid:
|
||||
RTMP_Log(RTMP_LOGDEBUG, "%s, invalid class encoding!",
|
||||
__FUNCTION__);
|
||||
return nOriginalSize;
|
||||
}
|
||||
len = AMF3ReadString(pBuffer, &memberName);
|
||||
RTMP_Log(RTMP_LOGDEBUG, "Member: %s", memberName.av_val);
|
||||
AMF3CD_AddProp(&cd, &memberName);
|
||||
|
|
@ -1115,6 +1146,8 @@ AMF3_Decode(AMFObject *obj, const char *pBuffer, int nSize, int bAMFData)
|
|||
int nRes, i;
|
||||
for (i = 0; i < cd.cd_num; i++) /* non-dynamic */
|
||||
{
|
||||
if (nSize <= 0)
|
||||
goto invalid;
|
||||
nRes = AMF3Prop_Decode(&prop, pBuffer, nSize, FALSE);
|
||||
if (nRes == -1)
|
||||
RTMP_Log(RTMP_LOGDEBUG, "%s, failed to decode AMF3 property!",
|
||||
|
|
@ -1132,6 +1165,8 @@ AMF3_Decode(AMFObject *obj, const char *pBuffer, int nSize, int bAMFData)
|
|||
|
||||
do
|
||||
{
|
||||
if (nSize <= 0)
|
||||
goto invalid;
|
||||
nRes = AMF3Prop_Decode(&prop, pBuffer, nSize, TRUE);
|
||||
AMF_AddProp(obj, &prop);
|
||||
|
||||
|
|
@ -1179,10 +1214,18 @@ AMF_Decode(AMFObject *obj, const char *pBuffer, int nSize, int bDecodeName)
|
|||
|
||||
nRes = AMFProp_Decode(&prop, pBuffer, nSize, bDecodeName);
|
||||
if (nRes == -1)
|
||||
{
|
||||
bError = TRUE;
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
nSize -= nRes;
|
||||
if (nSize < 0)
|
||||
{
|
||||
bError = TRUE;
|
||||
break;
|
||||
}
|
||||
pBuffer += nRes;
|
||||
AMF_AddProp(obj, &prop);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -21,7 +21,59 @@
|
|||
* http://www.gnu.org/copyleft/lgpl.html
|
||||
*/
|
||||
|
||||
#ifdef USE_POLARSSL
|
||||
#if defined(USE_MBEDTLS)
|
||||
#include <mbedtls/dhm.h>
|
||||
#include <mbedtls/bignum.h>
|
||||
typedef mbedtls_mpi* MP_t;
|
||||
#define MP_new(m) m = malloc(sizeof(mbedtls_mpi)); mbedtls_mpi_init(m)
|
||||
#define MP_set_w(mpi, w) mbedtls_mpi_lset(mpi, w)
|
||||
#define MP_cmp(u, v) mbedtls_mpi_cmp_mpi(u, v)
|
||||
#define MP_set(u, v) mbedtls_mpi_copy(u, v)
|
||||
#define MP_sub_w(mpi, w) mbedtls_mpi_sub_int(mpi, mpi, w)
|
||||
#define MP_cmp_1(mpi) mbedtls_mpi_cmp_int(mpi, 1)
|
||||
#define MP_modexp(r, y, q, p) mbedtls_mpi_exp_mod(r, y, q, p, NULL)
|
||||
#define MP_free(mpi) mbedtls_mpi_free(mpi); free(mpi)
|
||||
#define MP_gethex(u, hex, res) MP_new(u); res = mbedtls_mpi_read_string(u, 16, hex) == 0
|
||||
#define MP_bytes(u) mbedtls_mpi_size(u)
|
||||
#define MP_setbin(u,buf,len) mbedtls_mpi_write_binary(u,buf,len)
|
||||
#define MP_getbin(u,buf,len) MP_new(u); mbedtls_mpi_read_binary(u,buf,len)
|
||||
|
||||
typedef struct MDH
|
||||
{
|
||||
MP_t p;
|
||||
MP_t g;
|
||||
MP_t pub_key;
|
||||
MP_t priv_key;
|
||||
long length;
|
||||
mbedtls_dhm_context ctx;
|
||||
} MDH;
|
||||
|
||||
#define MDH_new() calloc(1,sizeof(MDH))
|
||||
#define MDH_free(vp) {MDH *_dh = vp; mbedtls_dhm_free(&_dh->ctx); MP_free(_dh->p); MP_free(_dh->g); MP_free(_dh->pub_key); MP_free(_dh->priv_key); free(_dh);}
|
||||
|
||||
static int MDH_generate_key(MDH *dh)
|
||||
{
|
||||
unsigned char out[2];
|
||||
MP_set(&dh->ctx.P, dh->p);
|
||||
MP_set(&dh->ctx.G, dh->g);
|
||||
dh->ctx.len = 128;
|
||||
mbedtls_dhm_make_public(&dh->ctx, 1024, out, 1, mbedtls_ctr_drbg_random, &RTMP_TLS_ctx->ctr_drbg);
|
||||
MP_new(dh->pub_key);
|
||||
MP_new(dh->priv_key);
|
||||
MP_set(dh->pub_key, &dh->ctx.GX);
|
||||
MP_set(dh->priv_key, &dh->ctx.X);
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int MDH_compute_key(uint8_t *secret, size_t len, MP_t pub, MDH *dh)
|
||||
{
|
||||
MP_set(&dh->ctx.GY, pub);
|
||||
size_t olen;
|
||||
mbedtls_dhm_calc_secret(&dh->ctx, secret, len, &olen, NULL, NULL);
|
||||
return 0;
|
||||
}
|
||||
|
||||
#elif defined(USE_POLARSSL)
|
||||
#include <polarssl/dhm.h>
|
||||
typedef mpi * MP_t;
|
||||
#define MP_new(m) m = malloc(sizeof(mpi)); mpi_init(m)
|
||||
|
|
@ -271,7 +323,7 @@ DHGetPublicKey(MDH *dh, uint8_t *pubkey, size_t nPubkeyLen)
|
|||
if (!dh || !dh->pub_key)
|
||||
return 0;
|
||||
|
||||
len = MP_bytes(dh->pub_key);
|
||||
len = (int)MP_bytes(dh->pub_key);
|
||||
if (len <= 0 || len > (int) nPubkeyLen)
|
||||
return 0;
|
||||
|
||||
|
|
|
|||
|
|
@ -24,7 +24,28 @@
|
|||
|
||||
/* This file is #included in rtmp.c, it is not meant to be compiled alone */
|
||||
|
||||
#ifdef USE_POLARSSL
|
||||
#if defined(USE_MBEDTLS)
|
||||
#include <mbedtls/md.h>
|
||||
#include <mbedtls/arc4.h>
|
||||
#ifndef SHA256_DIGEST_LENGTH
|
||||
#define SHA256_DIGEST_LENGTH 32
|
||||
#endif
|
||||
typedef mbedtls_md_context_t *HMAC_CTX;
|
||||
#define HMAC_setup(ctx, key, len) ctx = malloc(sizeof(mbedtls_md_context_t)); mbedtls_md_init(ctx); \
|
||||
mbedtls_md_setup(ctx, mbedtls_md_info_from_type(MBEDTLS_MD_SHA256), 1); \
|
||||
mbedtls_md_hmac_starts(ctx, (const unsigned char *)key, len)
|
||||
#define HMAC_crunch(ctx, buf, len) mbedtls_md_hmac_update(ctx, buf, len)
|
||||
#define HMAC_finish(ctx, dig, dlen) dlen = SHA256_DIGEST_LENGTH; mbedtls_md_hmac_finish(ctx, dig)
|
||||
#define HMAC_close(ctx) mbedtls_md_free(ctx); free(ctx); ctx = NULL
|
||||
|
||||
typedef mbedtls_arc4_context* RC4_handle;
|
||||
#define RC4_alloc(h) *h = malloc(sizeof(mbedtls_arc4_context)); mbedtls_arc4_init(*h)
|
||||
#define RC4_setkey(h,l,k) mbedtls_arc4_setup(h,k,l)
|
||||
#define RC4_encrypt(h,l,d) mbedtls_arc4_crypt(h,l,(unsigned char *)d,(unsigned char *)d)
|
||||
#define RC4_encrypt2(h,l,s,d) mbedtls_arc4_crypt(h,l,(unsigned char *)s,(unsigned char *)d)
|
||||
#define RC4_free(h) mbedtls_arc4_free(h); free(h); h = NULL
|
||||
|
||||
#elif defined(USE_POLARSSL)
|
||||
#include <polarssl/sha2.h>
|
||||
#include <polarssl/arc4.h>
|
||||
#ifndef SHA256_DIGEST_LENGTH
|
||||
|
|
@ -148,6 +169,8 @@ typedef unsigned int (getoff)(uint8_t *buf, unsigned int len);
|
|||
static unsigned int
|
||||
GetDHOffset2(uint8_t *handshake, unsigned int len)
|
||||
{
|
||||
(void) len;
|
||||
|
||||
unsigned int offset = 0;
|
||||
uint8_t *ptr = handshake + 768;
|
||||
unsigned int res;
|
||||
|
|
@ -177,6 +200,8 @@ GetDHOffset2(uint8_t *handshake, unsigned int len)
|
|||
static unsigned int
|
||||
GetDigestOffset2(uint8_t *handshake, unsigned int len)
|
||||
{
|
||||
(void) len;
|
||||
|
||||
unsigned int offset = 0;
|
||||
uint8_t *ptr = handshake + 772;
|
||||
unsigned int res;
|
||||
|
|
@ -206,6 +231,8 @@ GetDigestOffset2(uint8_t *handshake, unsigned int len)
|
|||
static unsigned int
|
||||
GetDHOffset1(uint8_t *handshake, unsigned int len)
|
||||
{
|
||||
(void) len;
|
||||
|
||||
unsigned int offset = 0;
|
||||
uint8_t *ptr = handshake + 1532;
|
||||
unsigned int res;
|
||||
|
|
@ -235,6 +262,8 @@ GetDHOffset1(uint8_t *handshake, unsigned int len)
|
|||
static unsigned int
|
||||
GetDigestOffset1(uint8_t *handshake, unsigned int len)
|
||||
{
|
||||
(void) len;
|
||||
|
||||
unsigned int offset = 0;
|
||||
uint8_t *ptr = handshake + 8;
|
||||
unsigned int res;
|
||||
|
|
@ -1128,6 +1157,7 @@ HandShake(RTMP * r, int FP9HandShake)
|
|||
__FUNCTION__);
|
||||
}
|
||||
}
|
||||
// TODO(mgoulet): Should this have a HMAC_finish here?
|
||||
|
||||
RTMP_Log(RTMP_LOGDEBUG, "%s: Handshaking finished....", __FUNCTION__);
|
||||
return TRUE;
|
||||
|
|
@ -1482,6 +1512,8 @@ SHandShake(RTMP * r)
|
|||
}
|
||||
}
|
||||
|
||||
// TODO(mgoulet): Should this have an Rc4_free?
|
||||
|
||||
RTMP_Log(RTMP_LOGDEBUG, "%s: Handshaking finished....", __FUNCTION__);
|
||||
return TRUE;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -30,7 +30,20 @@
|
|||
#pragma GCC diagnostic ignored "-Wdeprecated-declarations"
|
||||
#endif
|
||||
|
||||
#ifdef USE_POLARSSL
|
||||
#if defined(USE_MBEDTLS)
|
||||
#include <mbedtls/md.h>
|
||||
#ifndef SHA256_DIGEST_LENGTH
|
||||
#define SHA256_DIGEST_LENGTH 32
|
||||
#endif
|
||||
typedef mbedtls_md_context_t *HMAC_CTX;
|
||||
#define HMAC_setup(ctx, key, len) ctx = malloc(sizeof(mbedtls_md_context_t)); mbedtls_md_init(ctx); \
|
||||
mbedtls_md_setup(ctx, mbedtls_md_info_from_type(MBEDTLS_MD_SHA256), 1); \
|
||||
mbedtls_md_hmac_starts(ctx, (const unsigned char *)key, len)
|
||||
#define HMAC_crunch(ctx, buf, len) mbedtls_md_hmac_update(ctx, buf, len)
|
||||
#define HMAC_finish(ctx, dig, dlen) dlen = SHA256_DIGEST_LENGTH; mbedtls_md_hmac_finish(ctx, dig)
|
||||
#define HMAC_close(ctx) free(ctx); mbedtls_md_free(ctx); ctx = NULL
|
||||
|
||||
#elif defined(USE_POLARSSL)
|
||||
#include <polarssl/sha2.h>
|
||||
#ifndef SHA256_DIGEST_LENGTH
|
||||
#define SHA256_DIGEST_LENGTH 32
|
||||
|
|
@ -40,6 +53,7 @@
|
|||
#define HMAC_crunch(ctx, buf, len) sha2_hmac_update(&ctx, buf, len)
|
||||
#define HMAC_finish(ctx, dig, dlen) dlen = SHA256_DIGEST_LENGTH; sha2_hmac_finish(&ctx, dig)
|
||||
#define HMAC_close(ctx)
|
||||
|
||||
#elif defined(USE_GNUTLS)
|
||||
#include <nettle/hmac.h>
|
||||
#ifndef SHA256_DIGEST_LENGTH
|
||||
|
|
@ -51,6 +65,7 @@
|
|||
#define HMAC_crunch(ctx, buf, len) hmac_sha256_update(&ctx, len, buf)
|
||||
#define HMAC_finish(ctx, dig, dlen) dlen = SHA256_DIGEST_LENGTH; hmac_sha256_digest(&ctx, SHA256_DIGEST_LENGTH, dig)
|
||||
#define HMAC_close(ctx)
|
||||
|
||||
#else /* USE_OPENSSL */
|
||||
#include <openssl/ssl.h>
|
||||
#include <openssl/sha.h>
|
||||
|
|
@ -161,8 +176,17 @@ HTTP_get(struct HTTP_ctx *http, const char *url, HTTP_read_callback *cb)
|
|||
goto leave;
|
||||
#else
|
||||
TLS_client(RTMP_TLS_ctx, sb.sb_ssl);
|
||||
|
||||
#if defined(USE_MBEDTLS)
|
||||
mbedtls_net_context *server_fd = &RTMP_TLS_ctx->net;
|
||||
server_fd->fd = sb.sb_socket;
|
||||
TLS_setfd(sb.sb_ssl, server_fd);
|
||||
#else
|
||||
TLS_setfd(sb.sb_ssl, sb.sb_socket);
|
||||
if (TLS_connect(sb.sb_ssl) < 0)
|
||||
#endif
|
||||
|
||||
int connect_return = TLS_connect(sb.sb_ssl);
|
||||
if (connect_return < 0)
|
||||
{
|
||||
RTMP_Log(RTMP_LOGERROR, "%s, TLS_Connect failed", __FUNCTION__);
|
||||
ret = HTTPRES_LOST_CONNECTION;
|
||||
|
|
@ -318,21 +342,21 @@ swfcrunch(void *ptr, size_t size, size_t nmemb, void *stream)
|
|||
{
|
||||
unsigned char out[CHUNK];
|
||||
i->zs->next_in = (unsigned char *)p;
|
||||
i->zs->avail_in = len;
|
||||
i->zs->avail_in = (uInt)len;
|
||||
do
|
||||
{
|
||||
i->zs->avail_out = CHUNK;
|
||||
i->zs->next_out = out;
|
||||
inflate(i->zs, Z_NO_FLUSH);
|
||||
len = CHUNK - i->zs->avail_out;
|
||||
i->size += len;
|
||||
i->size += (int)len;
|
||||
HMAC_crunch(i->ctx, out, len);
|
||||
}
|
||||
while (i->zs->avail_out == 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
i->size += len;
|
||||
i->size += (int)len;
|
||||
HMAC_crunch(i->ctx, (unsigned char *)p, len);
|
||||
}
|
||||
return size * nmemb;
|
||||
|
|
@ -469,7 +493,7 @@ RTMP_HashSWF(const char *url, unsigned int *size, unsigned char *hash,
|
|||
home.av_val = "\\UserData";
|
||||
#else
|
||||
hpre.av_val = getenv("HOMEDRIVE");
|
||||
hpre.av_len = strlen(hpre.av_val);
|
||||
hpre.av_len = (int)strlen(hpre.av_val);
|
||||
home.av_val = getenv("HOMEPATH");
|
||||
#endif
|
||||
#define DIRSEP "\\"
|
||||
|
|
@ -482,7 +506,7 @@ RTMP_HashSWF(const char *url, unsigned int *size, unsigned char *hash,
|
|||
#endif
|
||||
if (!home.av_val)
|
||||
home.av_val = ".";
|
||||
home.av_len = strlen(home.av_val);
|
||||
home.av_len = (int)strlen(home.av_val);
|
||||
|
||||
/* SWF hash info is cached in a fixed-format file.
|
||||
* url: <url of SWF file>
|
||||
|
|
@ -528,7 +552,7 @@ RTMP_HashSWF(const char *url, unsigned int *size, unsigned char *hash,
|
|||
if (strncmp(buf + 5, url, hlen))
|
||||
continue;
|
||||
r1 = strrchr(buf, '/');
|
||||
i = strlen(r1);
|
||||
i = (int)strlen(r1);
|
||||
r1[--i] = '\0';
|
||||
if (strncmp(r1, file, i))
|
||||
continue;
|
||||
|
|
@ -543,7 +567,7 @@ RTMP_HashSWF(const char *url, unsigned int *size, unsigned char *hash,
|
|||
else if (!strncmp(buf, "hash: ", 6))
|
||||
{
|
||||
unsigned char *ptr = hash, *in = (unsigned char *)buf + 6;
|
||||
int l = strlen((char *)in) - 1;
|
||||
int l = (int)strlen((char *)in) - 1;
|
||||
for (i = 0; i < l; i += 2)
|
||||
*ptr++ = (HEX2BIN(in[i]) << 4) | HEX2BIN(in[i + 1]);
|
||||
got++;
|
||||
|
|
@ -625,7 +649,7 @@ RTMP_HashSWF(const char *url, unsigned int *size, unsigned char *hash,
|
|||
if (q)
|
||||
i = q - url;
|
||||
else
|
||||
i = strlen(url);
|
||||
i = (int)strlen(url);
|
||||
|
||||
fprintf(f, "url: %.*s\n", i, url);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -40,7 +40,20 @@
|
|||
#pragma GCC diagnostic ignored "-Wdeprecated-declarations"
|
||||
#endif
|
||||
|
||||
#ifdef USE_POLARSSL
|
||||
#if defined(USE_MBEDTLS)
|
||||
#if defined(_WIN32)
|
||||
#include <windows.h>
|
||||
#include <wincrypt.h>
|
||||
#elif defined(__APPLE__)
|
||||
#include <Security/Security.h>
|
||||
#endif
|
||||
|
||||
#include <mbedtls/ctr_drbg.h>
|
||||
#include <mbedtls/md5.h>
|
||||
#include <mbedtls/base64.h>
|
||||
#define MD5_DIGEST_LENGTH 16
|
||||
|
||||
#elif defined(USE_POLARSSL)
|
||||
#include <polarssl/havege.h>
|
||||
#include <polarssl/md5.h>
|
||||
#include <polarssl/base64.h>
|
||||
|
|
@ -57,7 +70,6 @@ static const char *my_dhm_P =
|
|||
"E8A700D60B7F1200FA8E77B0A979DABF";
|
||||
|
||||
static const char *my_dhm_G = "4";
|
||||
|
||||
#elif defined(USE_GNUTLS)
|
||||
#include <gnutls/gnutls.h>
|
||||
#define MD5_DIGEST_LENGTH 16
|
||||
|
|
@ -70,7 +82,8 @@ static const char *my_dhm_G = "4";
|
|||
#include <openssl/bio.h>
|
||||
#include <openssl/buffer.h>
|
||||
#endif
|
||||
TLS_CTX RTMP_TLS_ctx;
|
||||
|
||||
TLS_CTX RTMP_TLS_ctx = NULL;
|
||||
#endif
|
||||
|
||||
#define RTMP_SIG_SIZE 1536
|
||||
|
|
@ -226,9 +239,13 @@ RTMPPacket_Reset(RTMPPacket *p)
|
|||
}
|
||||
|
||||
int
|
||||
RTMPPacket_Alloc(RTMPPacket *p, int nSize)
|
||||
RTMPPacket_Alloc(RTMPPacket *p, uint32_t nSize)
|
||||
{
|
||||
char *ptr = calloc(1, nSize + RTMP_MAX_HEADER_SIZE);
|
||||
char *ptr;
|
||||
if (nSize > SIZE_MAX - RTMP_MAX_HEADER_SIZE)
|
||||
return FALSE;
|
||||
|
||||
ptr = calloc(1, nSize + RTMP_MAX_HEADER_SIZE);
|
||||
if (!ptr)
|
||||
return FALSE;
|
||||
p->m_body = ptr + RTMP_MAX_HEADER_SIZE;
|
||||
|
|
@ -261,11 +278,101 @@ RTMP_LibVersion()
|
|||
return RTMP_LIB_VERSION;
|
||||
}
|
||||
|
||||
void
|
||||
RTMP_TLS_LoadCerts() {
|
||||
#ifdef USE_MBEDTLS
|
||||
mbedtls_x509_crt *chain = RTMP_TLS_ctx->cacert = calloc(1, sizeof(struct mbedtls_x509_crt));
|
||||
mbedtls_x509_crt_init(chain);
|
||||
|
||||
#if defined(_WIN32)
|
||||
HCERTSTORE hCertStore;
|
||||
PCCERT_CONTEXT pCertContext = NULL;
|
||||
|
||||
if (!(hCertStore = CertOpenSystemStore((HCRYPTPROV)NULL, L"ROOT"))) {
|
||||
goto error;
|
||||
}
|
||||
|
||||
while (pCertContext = CertEnumCertificatesInStore(hCertStore, pCertContext)) {
|
||||
mbedtls_x509_crt_parse_der(chain,
|
||||
(unsigned char *)pCertContext->pbCertEncoded,
|
||||
pCertContext->cbCertEncoded);
|
||||
}
|
||||
|
||||
CertFreeCertificateContext(pCertContext);
|
||||
CertCloseStore(hCertStore, 0);
|
||||
#elif defined(__APPLE__)
|
||||
SecKeychainRef keychain_ref;
|
||||
CFMutableDictionaryRef search_settings_ref;
|
||||
CFArrayRef result_ref;
|
||||
|
||||
if (SecKeychainOpen("/System/Library/Keychains/SystemRootCertificates.keychain",
|
||||
&keychain_ref)
|
||||
!= errSecSuccess) {
|
||||
goto error;
|
||||
}
|
||||
|
||||
search_settings_ref = CFDictionaryCreateMutable(NULL, 0, NULL, NULL);
|
||||
CFDictionarySetValue(search_settings_ref, kSecClass, kSecClassCertificate);
|
||||
CFDictionarySetValue(search_settings_ref, kSecMatchLimit, kSecMatchLimitAll);
|
||||
CFDictionarySetValue(search_settings_ref, kSecReturnRef, kCFBooleanTrue);
|
||||
CFDictionarySetValue(search_settings_ref, kSecMatchSearchList,
|
||||
CFArrayCreate(NULL, (const void **)&keychain_ref, 1, NULL));
|
||||
|
||||
if (SecItemCopyMatching(search_settings_ref, (CFTypeRef *)&result_ref)
|
||||
!= errSecSuccess) {
|
||||
goto error;
|
||||
}
|
||||
|
||||
for (CFIndex i = 0; i < CFArrayGetCount(result_ref); i++) {
|
||||
SecCertificateRef item_ref = (SecCertificateRef)
|
||||
CFArrayGetValueAtIndex(result_ref, i);
|
||||
CFDataRef data_ref;
|
||||
|
||||
if ((data_ref = SecCertificateCopyData(item_ref))) {
|
||||
mbedtls_x509_crt_parse_der(chain,
|
||||
(unsigned char *)CFDataGetBytePtr(data_ref),
|
||||
CFDataGetLength(data_ref));
|
||||
CFRelease(data_ref);
|
||||
}
|
||||
}
|
||||
|
||||
CFRelease(keychain_ref);
|
||||
#elif defined(__linux__)
|
||||
if (mbedtls_x509_crt_parse_path(chain, "/etc/ssl/certs/") != 0) {
|
||||
goto error;
|
||||
}
|
||||
#endif
|
||||
|
||||
mbedtls_ssl_conf_ca_chain(&RTMP_TLS_ctx->conf, chain, NULL);
|
||||
return;
|
||||
|
||||
error:
|
||||
mbedtls_x509_crt_free(chain);
|
||||
free(chain);
|
||||
RTMP_TLS_ctx->cacert = NULL;
|
||||
#endif /* USE_MBEDTLS */
|
||||
}
|
||||
|
||||
void
|
||||
RTMP_TLS_Init()
|
||||
{
|
||||
#ifdef CRYPTO
|
||||
#ifdef USE_POLARSSL
|
||||
#if defined(USE_MBEDTLS)
|
||||
const char * pers = "RTMP_TLS";
|
||||
RTMP_TLS_ctx = calloc(1,sizeof(struct tls_ctx));
|
||||
|
||||
mbedtls_ssl_config_init(&RTMP_TLS_ctx->conf);
|
||||
mbedtls_ctr_drbg_init(&RTMP_TLS_ctx->ctr_drbg);
|
||||
mbedtls_entropy_init(&RTMP_TLS_ctx->entropy);
|
||||
|
||||
mbedtls_ctr_drbg_seed(&RTMP_TLS_ctx->ctr_drbg,
|
||||
mbedtls_entropy_func,
|
||||
&RTMP_TLS_ctx->entropy,
|
||||
(const unsigned char *)pers,
|
||||
strlen(pers));
|
||||
|
||||
RTMP_TLS_LoadCerts();
|
||||
#elif defined(USE_POLARSSL)
|
||||
/* Do this regardless of NO_SSL, we use havege for rtmpe too */
|
||||
RTMP_TLS_ctx = calloc(1,sizeof(struct tls_ctx));
|
||||
havege_init(&RTMP_TLS_ctx->hs);
|
||||
|
|
@ -289,6 +396,26 @@ RTMP_TLS_Init()
|
|||
SSL_CTX_set_options(RTMP_TLS_ctx, SSL_OP_ALL);
|
||||
SSL_CTX_set_default_verify_paths(RTMP_TLS_ctx);
|
||||
#endif
|
||||
#else
|
||||
#endif
|
||||
}
|
||||
|
||||
void
|
||||
RTMP_TLS_Free() {
|
||||
#ifdef USE_MBEDTLS
|
||||
mbedtls_ssl_config_free(&RTMP_TLS_ctx->conf);
|
||||
mbedtls_ctr_drbg_free(&RTMP_TLS_ctx->ctr_drbg);
|
||||
mbedtls_entropy_free(&RTMP_TLS_ctx->entropy);
|
||||
|
||||
if (RTMP_TLS_ctx->cacert) {
|
||||
mbedtls_x509_crt_free(RTMP_TLS_ctx->cacert);
|
||||
free(RTMP_TLS_ctx->cacert);
|
||||
RTMP_TLS_ctx->cacert = NULL;
|
||||
}
|
||||
|
||||
// NO mbedtls_net_free() BECAUSE WE SET IT UP BY HAND!
|
||||
free(RTMP_TLS_ctx);
|
||||
RTMP_TLS_ctx = NULL;
|
||||
#endif
|
||||
}
|
||||
|
||||
|
|
@ -299,7 +426,27 @@ RTMP_TLS_AllocServerContext(const char* cert, const char* key)
|
|||
#ifdef CRYPTO
|
||||
if (!RTMP_TLS_ctx)
|
||||
RTMP_TLS_Init();
|
||||
#ifdef USE_POLARSSL
|
||||
#if defined(USE_MBEDTLS)
|
||||
tls_server_ctx *tc = ctx = calloc(1, sizeof(struct tls_server_ctx));
|
||||
tc->conf = &RTMP_TLS_ctx->conf;
|
||||
tc->ctr_drbg = &RTMP_TLS_ctx->ctr_drbg;
|
||||
|
||||
mbedtls_x509_crt_init(&tc->cert);
|
||||
if (mbedtls_x509_crt_parse_file(&tc->cert, cert))
|
||||
{
|
||||
free(tc);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
mbedtls_pk_init(&tc->key);
|
||||
if (mbedtls_pk_parse_keyfile(&tc->key, key, NULL))
|
||||
{
|
||||
mbedtls_x509_crt_free(&tc->cert);
|
||||
mbedtls_pk_free(&tc->key);
|
||||
free(tc);
|
||||
return NULL;
|
||||
}
|
||||
#elif defined(USE_POLARSSL)
|
||||
tls_server_ctx *tc = ctx = calloc(1, sizeof(struct tls_server_ctx));
|
||||
tc->dhm_P = my_dhm_P;
|
||||
tc->dhm_G = my_dhm_G;
|
||||
|
|
@ -346,7 +493,11 @@ void
|
|||
RTMP_TLS_FreeServerContext(void *ctx)
|
||||
{
|
||||
#ifdef CRYPTO
|
||||
#ifdef USE_POLARSSL
|
||||
#if defined(USE_MBEDTLS)
|
||||
mbedtls_x509_crt_free(&((tls_server_ctx*)ctx)->cert);
|
||||
mbedtls_pk_free(&((tls_server_ctx*)ctx)->key);
|
||||
free(ctx);
|
||||
#elif defined(USE_POLARSSL)
|
||||
x509_free(&((tls_server_ctx*)ctx)->cert);
|
||||
rsa_free(&((tls_server_ctx*)ctx)->key);
|
||||
free(ctx);
|
||||
|
|
@ -370,6 +521,10 @@ RTMP_Alloc()
|
|||
void
|
||||
RTMP_Free(RTMP *r)
|
||||
{
|
||||
#if defined(CRYPTO) && defined(USE_MBEDTLS)
|
||||
if (RTMP_TLS_ctx)
|
||||
RTMP_TLS_Free();
|
||||
#endif
|
||||
free(r);
|
||||
}
|
||||
|
||||
|
|
@ -846,9 +1001,20 @@ int
|
|||
RTMP_TLS_Accept(RTMP *r, void *ctx)
|
||||
{
|
||||
#if defined(CRYPTO) && !defined(NO_SSL)
|
||||
TLS_server(ctx, r->m_sb.sb_ssl);
|
||||
tls_server_ctx *srv_ctx = ctx;
|
||||
TLS_server(srv_ctx, r->m_sb.sb_ssl);
|
||||
|
||||
#if defined(USE_MBEDTLS)
|
||||
mbedtls_net_context *client_fd = &RTMP_TLS_ctx->net;
|
||||
mbedtls_net_init(client_fd);
|
||||
client_fd->fd = r->m_sb.sb_socket;
|
||||
TLS_setfd(r->m_sb.sb_ssl, client_fd);
|
||||
#else
|
||||
TLS_setfd(r->m_sb.sb_ssl, r->m_sb.sb_socket);
|
||||
if (TLS_accept(r->m_sb.sb_ssl) < 0)
|
||||
#endif
|
||||
|
||||
int connect_return = TLS_connect(r->m_sb.sb_ssl);
|
||||
if (connect_return < 0)
|
||||
{
|
||||
RTMP_Log(RTMP_LOGERROR, "%s, TLS_Connect failed", __FUNCTION__);
|
||||
return FALSE;
|
||||
|
|
@ -868,10 +1034,59 @@ RTMP_Connect1(RTMP *r, RTMPPacket *cp)
|
|||
{
|
||||
#if defined(CRYPTO) && !defined(NO_SSL)
|
||||
TLS_client(RTMP_TLS_ctx, r->m_sb.sb_ssl);
|
||||
|
||||
#if defined(USE_MBEDTLS)
|
||||
mbedtls_net_context *server_fd = &RTMP_TLS_ctx->net;
|
||||
server_fd->fd = r->m_sb.sb_socket;
|
||||
TLS_setfd(r->m_sb.sb_ssl, server_fd);
|
||||
|
||||
// make sure we verify the certificate hostname
|
||||
char hostname[MBEDTLS_SSL_MAX_HOST_NAME_LEN + 1];
|
||||
|
||||
if (r->Link.hostname.av_len >= MBEDTLS_SSL_MAX_HOST_NAME_LEN)
|
||||
return FALSE;
|
||||
|
||||
memcpy(hostname, r->Link.hostname.av_val, r->Link.hostname.av_len);
|
||||
hostname[r->Link.hostname.av_len] = 0;
|
||||
|
||||
if (mbedtls_ssl_set_hostname(r->m_sb.sb_ssl, hostname))
|
||||
return FALSE;
|
||||
#else
|
||||
TLS_setfd(r->m_sb.sb_ssl, r->m_sb.sb_socket);
|
||||
if (TLS_connect(r->m_sb.sb_ssl) < 0)
|
||||
#endif
|
||||
|
||||
int connect_return = TLS_connect(r->m_sb.sb_ssl);
|
||||
if (connect_return < 0)
|
||||
{
|
||||
RTMP_Log(RTMP_LOGERROR, "%s, TLS_Connect failed", __FUNCTION__);
|
||||
#if defined(USE_MBEDTLS)
|
||||
if (connect_return == MBEDTLS_ERR_X509_CERT_VERIFY_FAILED)
|
||||
{
|
||||
r->last_error_code = connect_return;
|
||||
|
||||
// show a more detailed error in the log if possible
|
||||
int verify_result = mbedtls_ssl_get_verify_result(r->m_sb.sb_ssl);
|
||||
if (verify_result)
|
||||
{
|
||||
char err[256], *e;
|
||||
if (mbedtls_x509_crt_verify_info(err, sizeof(err), "", verify_result) > 0)
|
||||
{
|
||||
e = strchr(err, '\n');
|
||||
if (e)
|
||||
*e = '\0';
|
||||
}
|
||||
else
|
||||
{
|
||||
strcpy(err, "unknown error");
|
||||
}
|
||||
RTMP_Log(RTMP_LOGERROR, "%s, Cert verify failed: %d (%s)", __FUNCTION__, verify_result, err);
|
||||
RTMP_Close(r);
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
// output the error in a format that matches mbedTLS
|
||||
connect_return = abs(connect_return);
|
||||
RTMP_Log(RTMP_LOGERROR, "%s, TLS_Connect failed: -0x%x", __FUNCTION__, connect_return);
|
||||
RTMP_Close(r);
|
||||
return FALSE;
|
||||
}
|
||||
|
|
@ -879,7 +1094,6 @@ RTMP_Connect1(RTMP *r, RTMPPacket *cp)
|
|||
RTMP_Log(RTMP_LOGERROR, "%s, no SSL/TLS support", __FUNCTION__);
|
||||
RTMP_Close(r);
|
||||
return FALSE;
|
||||
|
||||
#endif
|
||||
}
|
||||
if (r->Link.protocol & RTMP_FEATURE_HTTP)
|
||||
|
|
@ -1108,7 +1322,7 @@ RTMP_GetNextMediaPacket(RTMP *r, RTMPPacket *packet)
|
|||
while (!bHasMediaPacket && RTMP_IsConnected(r)
|
||||
&& RTMP_ReadPacket(r, packet))
|
||||
{
|
||||
if (!RTMPPacket_IsReady(packet))
|
||||
if (!RTMPPacket_IsReady(packet) || !packet->m_nBodySize)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
|
@ -2398,7 +2612,19 @@ b64enc(const unsigned char *input, int length, char *output, int maxsize)
|
|||
{
|
||||
(void)maxsize;
|
||||
|
||||
#ifdef USE_POLARSSL
|
||||
#if defined(USE_MBEDTLS)
|
||||
size_t osize;
|
||||
if(mbedtls_base64_encode((unsigned char *) output, maxsize, &osize, input, length) == 0)
|
||||
{
|
||||
output[osize] = '\0';
|
||||
return 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
RTMP_Log(RTMP_LOGDEBUG, "%s, error", __FUNCTION__);
|
||||
return 0;
|
||||
}
|
||||
#elif defined(USE_POLARSSL)
|
||||
size_t buf_size = maxsize;
|
||||
if(base64_encode((unsigned char *) output, &buf_size, input, length) == 0)
|
||||
{
|
||||
|
|
@ -2457,7 +2683,13 @@ b64enc(const unsigned char *input, int length, char *output, int maxsize)
|
|||
return 1;
|
||||
}
|
||||
|
||||
#ifdef USE_POLARSSL
|
||||
#if defined(USE_MBEDTLS)
|
||||
typedef mbedtls_md5_context MD5_CTX;
|
||||
#define MD5_Init(ctx) mbedtls_md5_init(ctx); mbedtls_md5_starts(ctx)
|
||||
#define MD5_Update(ctx,data,len) mbedtls_md5_update(ctx,(unsigned char *)data,len)
|
||||
#define MD5_Final(dig,ctx) mbedtls_md5_finish(ctx,dig); mbedtls_md5_free(ctx)
|
||||
|
||||
#elif defined(USE_POLARSSL)
|
||||
#define MD5_CTX md5_context
|
||||
#define MD5_Init(ctx) md5_starts(ctx)
|
||||
#define MD5_Update(ctx,data,len) md5_update(ctx,(unsigned char *)data,len)
|
||||
|
|
@ -3713,7 +3945,6 @@ RTMP_ReadPacket(RTMP *r, RTMPPacket *packet)
|
|||
{
|
||||
packet->m_nBodySize = AMF_DecodeInt24(header + 3);
|
||||
packet->m_nBytesRead = 0;
|
||||
RTMPPacket_Free(packet);
|
||||
|
||||
if (nSize > 6)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -150,7 +150,7 @@ extern "C"
|
|||
|
||||
void RTMPPacket_Reset(RTMPPacket *p);
|
||||
void RTMPPacket_Dump(RTMPPacket *p);
|
||||
int RTMPPacket_Alloc(RTMPPacket *p, int nSize);
|
||||
int RTMPPacket_Alloc(RTMPPacket *p, uint32_t nSize);
|
||||
void RTMPPacket_Free(RTMPPacket *p);
|
||||
|
||||
#define RTMPPacket_IsReady(a) ((a)->m_nBytesRead == (a)->m_nBodySize)
|
||||
|
|
|
|||
|
|
@ -80,7 +80,76 @@
|
|||
|
||||
#include "rtmp.h"
|
||||
|
||||
#ifdef USE_POLARSSL
|
||||
#if defined(USE_MBEDTLS)
|
||||
#include <mbedtls/version.h>
|
||||
#include <mbedtls/net.h>
|
||||
#include <mbedtls/ssl.h>
|
||||
#include <mbedtls/ctr_drbg.h>
|
||||
#include <mbedtls/entropy.h>
|
||||
|
||||
#define my_dhm_P \
|
||||
"E4004C1F94182000103D883A448B3F80" \
|
||||
"2CE4B44A83301270002C20D0321CFD00" \
|
||||
"11CCEF784C26A400F43DFB901BCA7538" \
|
||||
"F2C6B176001CF5A0FD16D2C48B1D0C1C" \
|
||||
"F6AC8E1DA6BCC3B4E1F96B0564965300" \
|
||||
"FFA1D0B601EB2800F489AA512C4B248C" \
|
||||
"01F76949A60BB7F00A40B1EAB64BDD48" \
|
||||
"E8A700D60B7F1200FA8E77B0A979DABF"
|
||||
|
||||
#define my_dhm_G "4"
|
||||
|
||||
#define SSL_SET_SESSION(S,resume,timeout,ctx) mbedtls_ssl_set_session(S,ctx)
|
||||
|
||||
typedef struct tls_ctx
|
||||
{
|
||||
mbedtls_entropy_context entropy;
|
||||
mbedtls_ctr_drbg_context ctr_drbg;
|
||||
mbedtls_ssl_config conf;
|
||||
mbedtls_ssl_session ssn;
|
||||
mbedtls_x509_crt *cacert;
|
||||
mbedtls_net_context net;
|
||||
} tls_ctx;
|
||||
|
||||
typedef struct tls_server_ctx
|
||||
{
|
||||
mbedtls_ssl_config *conf;
|
||||
mbedtls_ctr_drbg_context *ctr_drbg;
|
||||
mbedtls_pk_context key;
|
||||
mbedtls_x509_crt cert;
|
||||
} tls_server_ctx;
|
||||
|
||||
typedef tls_ctx *TLS_CTX;
|
||||
|
||||
#define TLS_client(ctx,s) \
|
||||
s = malloc(sizeof(mbedtls_ssl_context));\
|
||||
mbedtls_ssl_init(s);\
|
||||
mbedtls_ssl_setup(s, &ctx->conf);\
|
||||
mbedtls_ssl_config_defaults(&ctx->conf, MBEDTLS_SSL_IS_CLIENT, MBEDTLS_SSL_TRANSPORT_STREAM, MBEDTLS_SSL_PRESET_DEFAULT);\
|
||||
mbedtls_ssl_conf_authmode(&ctx->conf, MBEDTLS_SSL_VERIFY_REQUIRED);\
|
||||
mbedtls_ssl_conf_rng(&ctx->conf, mbedtls_ctr_drbg_random, &ctx->ctr_drbg)
|
||||
|
||||
#define TLS_server(ctx,s)\
|
||||
s = malloc(sizeof(mbedtls_ssl_context));\
|
||||
mbedtls_ssl_init(s);\
|
||||
mbedtls_ssl_setup(s, ctx->conf);\
|
||||
mbedtls_ssl_conf_endpoint(ctx->conf, MBEDTLS_SSL_IS_SERVER);\
|
||||
mbedtls_ssl_conf_authmode(ctx->conf, MBEDTLS_SSL_VERIFY_REQUIRED);\
|
||||
mbedtls_ssl_conf_rng(ctx->conf, mbedtls_ctr_drbg_random, ctx->ctr_drbg);\
|
||||
mbedtls_ssl_conf_own_cert(ctx->conf, &ctx->cert, &ctx->key);\
|
||||
mbedtls_ssl_conf_dh_param_bin(ctx->conf,\
|
||||
(const unsigned char *)my_dhm_P, strlen(my_dhm_P),\
|
||||
(const unsigned char *)my_dhm_G, strlen(my_dhm_G))
|
||||
|
||||
#define TLS_setfd(s,fd) mbedtls_ssl_set_bio(s, fd, mbedtls_net_send, mbedtls_net_recv, NULL)
|
||||
#define TLS_connect(s) mbedtls_ssl_handshake(s)
|
||||
#define TLS_accept(s) mbedtls_ssl_handshake(s)
|
||||
#define TLS_read(s,b,l) mbedtls_ssl_read(s,(unsigned char *)b,l)
|
||||
#define TLS_write(s,b,l) mbedtls_ssl_write(s,(unsigned char *)b,l)
|
||||
#define TLS_shutdown(s) mbedtls_ssl_close_notify(s)
|
||||
#define TLS_close(s) mbedtls_ssl_free(s); free(s)
|
||||
|
||||
#elif defined(USE_POLARSSL)
|
||||
#include <polarssl/version.h>
|
||||
#include <polarssl/net.h>
|
||||
#include <polarssl/ssl.h>
|
||||
|
|
@ -128,6 +197,7 @@ typedef struct tls_server_ctx
|
|||
#define TLS_shutdown(s) ssl_close_notify(s)
|
||||
#define TLS_close(s) ssl_free(s); free(s)
|
||||
|
||||
|
||||
#elif defined(USE_GNUTLS)
|
||||
#include <gnutls/gnutls.h>
|
||||
typedef struct tls_ctx
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue