⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 kssl.c

📁 mediastreamer2是开源的网络传输媒体流的库
💻 C
📖 第 1 页 / 共 5 页
字号:
	if ((krb5rc = kssl_build_principal_2(krb5context,			&new5ticket->server,			asn1ticket->realm->length, (char *)asn1ticket->realm->data,			gstr_svc->length,  (char *)gstr_svc->data,			gstr_host->length, (char *)gstr_host->data)) != 0)		{		free(new5ticket);		BIO_snprintf(kssl_err->text, KSSL_ERR_MAX,			"Error building ticket server principal.\n");		kssl_err->reason = SSL_R_KRB5_S_RD_REQ;		return krb5rc;		/*  or  KRB5KRB_ERR_GENERIC;	*/		}	krb5_princ_type(krb5context, new5ticket->server) =			asn1ticket->sname->nametype->data[0];	new5ticket->enc_part.enctype = asn1ticket->encdata->etype->data[0];	new5ticket->enc_part.kvno = asn1ticket->encdata->kvno->data[0];	new5ticket->enc_part.ciphertext.length =			asn1ticket->encdata->cipher->length;	if ((new5ticket->enc_part.ciphertext.data =		calloc(1, asn1ticket->encdata->cipher->length)) == NULL)		{		free(new5ticket);		BIO_snprintf(kssl_err->text, KSSL_ERR_MAX,			"Error allocating cipher in krb5ticket.\n");		kssl_err->reason = SSL_R_KRB5_S_RD_REQ;		return KRB5KRB_ERR_GENERIC;		}	else		{		memcpy(new5ticket->enc_part.ciphertext.data,			asn1ticket->encdata->cipher->data,			asn1ticket->encdata->cipher->length);		}	*krb5ticket = new5ticket;	return 0;	}/*	Given krb5 service name in KSSL_CTX *kssl_ctx (typically "kssl"),**		and krb5 AP_REQ message & message length,**	Return Kerberos session key and client principle**		to SSL Server in KSSL_CTX *kssl_ctx.****	19990702	VRS 	Started.*/krb5_error_codekssl_sget_tkt(	/* UPDATE */	KSSL_CTX		*kssl_ctx,		/* IN     */	krb5_data		*indata,		/* OUT    */	krb5_ticket_times	*ttimes,		/* OUT    */	KSSL_ERR		*kssl_err  )        {        krb5_error_code			krb5rc = KRB5KRB_ERR_GENERIC;        static krb5_context		krb5context = NULL;	static krb5_auth_context	krb5auth_context = NULL;	krb5_ticket 			*krb5ticket = NULL;	KRB5_TKTBODY 			*asn1ticket = NULL;	const unsigned char		*p;	krb5_keytab 			krb5keytab = NULL;	krb5_keytab_entry		kt_entry;	krb5_principal			krb5server;        krb5_rcache                     rcache = NULL;	kssl_err_set(kssl_err, 0, "");	if (!kssl_ctx)                {		kssl_err_set(kssl_err, SSL_R_KRB5_S_INIT,			"No kssl_ctx defined.\n");		goto err;		}#ifdef KSSL_DEBUG	printf("in kssl_sget_tkt(%s)\n", kstring(kssl_ctx->service_name));#endif	/* KSSL_DEBUG */	if (!krb5context  &&  (krb5rc = krb5_init_context(&krb5context)))                {		kssl_err_set(kssl_err, SSL_R_KRB5_S_INIT,                        "krb5_init_context() fails.\n");		goto err;		}	if (krb5auth_context  &&		(krb5rc = krb5_auth_con_free(krb5context, krb5auth_context)))                {		kssl_err_set(kssl_err, SSL_R_KRB5_S_INIT,                        "krb5_auth_con_free() fails.\n");		goto err;		}	else  krb5auth_context = NULL;	if (!krb5auth_context  &&		(krb5rc = krb5_auth_con_init(krb5context, &krb5auth_context)))                {		kssl_err_set(kssl_err, SSL_R_KRB5_S_INIT,                        "krb5_auth_con_init() fails.\n");		goto err;		} 	if ((krb5rc = krb5_auth_con_getrcache(krb5context, krb5auth_context,		&rcache)))		{ 		kssl_err_set(kssl_err, SSL_R_KRB5_S_INIT,			"krb5_auth_con_getrcache() fails.\n"); 		goto err;		} 	if ((krb5rc = krb5_sname_to_principal(krb5context, NULL,                (kssl_ctx->service_name)? kssl_ctx->service_name: KRB5SVC,                KRB5_NT_SRV_HST, &krb5server)) != 0)                {		kssl_err_set(kssl_err, SSL_R_KRB5_S_INIT,                        "krb5_sname_to_principal() fails.\n");		goto err;		}	if (rcache == NULL)                 {                if ((krb5rc = krb5_get_server_rcache(krb5context,			krb5_princ_component(krb5context, krb5server, 0),			&rcache)))                        {		        kssl_err_set(kssl_err, SSL_R_KRB5_S_INIT,                                "krb5_get_server_rcache() fails.\n");                  	goto err;                        }                }        if ((krb5rc = krb5_auth_con_setrcache(krb5context, krb5auth_context, rcache)))                {                kssl_err_set(kssl_err, SSL_R_KRB5_S_INIT,			"krb5_auth_con_setrcache() fails.\n");                goto err;                }	/*	kssl_ctx->keytab_file == NULL ==> use Kerberos default	*/	if (kssl_ctx->keytab_file)		{		krb5rc = krb5_kt_resolve(krb5context, kssl_ctx->keytab_file,                        &krb5keytab);		if (krb5rc)			{			kssl_err_set(kssl_err, SSL_R_KRB5_S_INIT,				"krb5_kt_resolve() fails.\n");			goto err;			}		}	else		{                krb5rc = krb5_kt_default(krb5context,&krb5keytab);                if (krb5rc)			{			kssl_err_set(kssl_err, SSL_R_KRB5_S_INIT, 				"krb5_kt_default() fails.\n");			goto err;			}		}	/*	Actual Kerberos5 krb5_recvauth() has initial conversation here	**	o	check KRB5_SENDAUTH_BADAUTHVERS	**		unless KRB5_RECVAUTH_SKIP_VERSION	**	o	check KRB5_SENDAUTH_BADAPPLVERS	**	o	send "0" msg if all OK	*/	/*  20010411 was using AP_REQ instead of true KerberosWrapper	**	**  if ((krb5rc = krb5_rd_req(krb5context, &krb5auth_context,	**			&krb5in_data, krb5server, krb5keytab,	**			&ap_option, &krb5ticket)) != 0)  { Error }	*/	p = (unsigned char *)indata->data;	if ((asn1ticket = (KRB5_TKTBODY *) d2i_KRB5_TICKET(NULL, &p,						(long) indata->length)) == NULL)		{		BIO_snprintf(kssl_err->text, KSSL_ERR_MAX,			"d2i_KRB5_TICKET() ASN.1 decode failure.\n");		kssl_err->reason = SSL_R_KRB5_S_RD_REQ;		goto err;		}		/* Was:  krb5rc = krb5_decode_ticket(krb5in_data,&krb5ticket)) != 0) */	if ((krb5rc = kssl_TKT2tkt(krb5context, asn1ticket, &krb5ticket,					kssl_err)) != 0)		{		BIO_snprintf(kssl_err->text, KSSL_ERR_MAX,			"Error converting ASN.1 ticket to krb5_ticket.\n");		kssl_err->reason = SSL_R_KRB5_S_RD_REQ;		goto err;		}	if (! krb5_principal_compare(krb5context, krb5server,						  krb5ticket->server))  {		krb5rc = KRB5_PRINC_NOMATCH;		BIO_snprintf(kssl_err->text, KSSL_ERR_MAX,			"server principal != ticket principal\n");		kssl_err->reason = SSL_R_KRB5_S_RD_REQ;		goto err;		}	if ((krb5rc = krb5_kt_get_entry(krb5context, krb5keytab,			krb5ticket->server, krb5ticket->enc_part.kvno,			krb5ticket->enc_part.enctype, &kt_entry)) != 0)  {		BIO_snprintf(kssl_err->text, KSSL_ERR_MAX,			"krb5_kt_get_entry() fails with %x.\n", krb5rc);		kssl_err->reason = SSL_R_KRB5_S_RD_REQ;		goto err;		}	if ((krb5rc = krb5_decrypt_tkt_part(krb5context, &kt_entry.key,			krb5ticket)) != 0)  {		BIO_snprintf(kssl_err->text, KSSL_ERR_MAX,			"krb5_decrypt_tkt_part() failed.\n");		kssl_err->reason = SSL_R_KRB5_S_RD_REQ;		goto err;		}	else  {		krb5_kt_free_entry(krb5context, &kt_entry);#ifdef KSSL_DEBUG		{		int i; krb5_address **paddr = krb5ticket->enc_part2->caddrs;		printf("Decrypted ticket fields:\n");		printf("\tflags: %X, transit-type: %X",			krb5ticket->enc_part2->flags,			krb5ticket->enc_part2->transited.tr_type);		print_krb5_data("\ttransit-data: ",			&(krb5ticket->enc_part2->transited.tr_contents));		printf("\tcaddrs: %p, authdata: %p\n",			krb5ticket->enc_part2->caddrs,			krb5ticket->enc_part2->authorization_data);		if (paddr)			{			printf("\tcaddrs:\n");			for (i=0; paddr[i] != NULL; i++)				{				krb5_data d;				d.length=paddr[i]->length;				d.data=paddr[i]->contents;				print_krb5_data("\t\tIP: ", &d);				}			}		printf("\tstart/auth/end times: %d / %d / %d\n",			krb5ticket->enc_part2->times.starttime,			krb5ticket->enc_part2->times.authtime,			krb5ticket->enc_part2->times.endtime);		}#endif	/* KSSL_DEBUG */		}	krb5rc = KRB5_NO_TKT_SUPPLIED;	if (!krb5ticket  ||	!krb5ticket->enc_part2  ||                !krb5ticket->enc_part2->client  ||                !krb5ticket->enc_part2->client->data  ||                !krb5ticket->enc_part2->session)                {                kssl_err_set(kssl_err, SSL_R_KRB5_S_BAD_TICKET,                        "bad ticket from krb5_rd_req.\n");		}	else if (kssl_ctx_setprinc(kssl_ctx, KSSL_CLIENT,		 &krb5ticket->enc_part2->client->realm,		 krb5ticket->enc_part2->client->data,		 krb5ticket->enc_part2->client->length))                {		kssl_err_set(kssl_err, SSL_R_KRB5_S_BAD_TICKET,                        "kssl_ctx_setprinc() fails.\n");		}	else if (kssl_ctx_setkey(kssl_ctx, krb5ticket->enc_part2->session))                {		kssl_err_set(kssl_err, SSL_R_KRB5_S_BAD_TICKET,                        "kssl_ctx_setkey() fails.\n");		}	else if (krb5ticket->enc_part2->flags & TKT_FLG_INVALID)                {		krb5rc = KRB5KRB_AP_ERR_TKT_INVALID;                kssl_err_set(kssl_err, SSL_R_KRB5_S_BAD_TICKET,                        "invalid ticket from krb5_rd_req.\n");		}	else	krb5rc = 0;	kssl_ctx->enctype	= krb5ticket->enc_part.enctype;	ttimes->authtime	= krb5ticket->enc_part2->times.authtime;	ttimes->starttime	= krb5ticket->enc_part2->times.starttime;	ttimes->endtime 	= krb5ticket->enc_part2->times.endtime;	ttimes->renew_till	= krb5ticket->enc_part2->times.renew_till; err:#ifdef KSSL_DEBUG	kssl_ctx_show(kssl_ctx);#endif	/* KSSL_DEBUG */	if (asn1ticket) 	KRB5_TICKET_free((KRB5_TICKET *) asn1ticket);        if (krb5keytab)         krb5_kt_close(krb5context, krb5keytab);	if (krb5ticket) 	krb5_free_ticket(krb5context, krb5ticket);	if (krb5server) 	krb5_free_principal(krb5context, krb5server);	return (krb5rc);        }/*	Allocate & return a new kssl_ctx struct.*/KSSL_CTX	*kssl_ctx_new(void)        {	return ((KSSL_CTX *) calloc(1, sizeof(KSSL_CTX)));        }/*	Frees a kssl_ctx struct and any allocated memory it holds.**	Returns NULL.*/KSSL_CTX	*kssl_ctx_free(KSSL_CTX *kssl_ctx)        {	if (kssl_ctx == NULL)  return kssl_ctx;	if (kssl_ctx->key)  		OPENSSL_cleanse(kssl_ctx->key,							      kssl_ctx->length);	if (kssl_ctx->key)  		free(kssl_ctx->key);	if (kssl_ctx->client_princ) 	free(kssl_ctx->client_princ);	if (kssl_ctx->service_host) 	free(kssl_ctx->service_host);	if (kssl_ctx->service_name) 	free(kssl_ctx->service_name);	if (kssl_ctx->keytab_file) 	free(kssl_ctx->keytab_file);	free(kssl_ctx);	return (KSSL_CTX *) NULL;        }/*	Given an array of (krb5_data *) entity (and optional realm),**	set the plain (char *) client_princ or service_host member**	of the kssl_ctx struct.*/krb5_error_codekssl_ctx_setprinc(KSSL_CTX *kssl_ctx, int which,        krb5_data *realm, krb5_data *entity, int nentities)        {	char	**princ;	int 	length;	int i;	if (kssl_ctx == NULL  ||  entity == NULL)  return KSSL_CTX_ERR;	switch (which)                {        case KSSL_CLIENT:	princ = &kssl_ctx->client_princ;	break;        case KSSL_SERVER:	princ = &kssl_ctx->service_host;	break;        default:		return KSSL_CTX_ERR;			break;		}	if (*princ)  free(*princ);	/* Add up all the entity->lengths */	length = 0;	for (i=0; i < nentities; i++)		{		length += entity[i].length;		}	/* Add in space for the '/' character(s) (if any) */	length += nentities-1;	/* Space for the ('@'+realm+NULL | NULL) */	length += ((realm)? realm->length + 2: 1);	if ((*princ = calloc(1, length)) == NULL)		return KSSL_CTX_ERR;	else		{		for (i = 0; i < nentities; i++)			{			strncat(*princ, entity[i].data, entity[i].length);			if (i < nentities-1)				{				strcat (*princ, "/");				}			}		if (realm)                        {			strcat (*princ, "@");			(void) strncat(*princ, realm->data, realm->length);			}		}	return KSSL_CTX_OK;        }/*	Set one of the plain (char *) string members of the kssl_ctx struct.**	Default values should be:**		which == KSSL_SERVICE	=>	"khost" (KRB5SVC)**		which == KSSL_KEYTAB	=>	"/etc/krb5.keytab" (KRB5KEYTAB)*/krb5_error_codekssl_ctx_setstring(KSSL_CTX *kssl_ctx, int which, char *text)        {	char	**string;	if (!kssl_ctx)  return KSSL_CTX_ERR;	switch (which)                {        case KSSL_SERVICE:	string = &kssl_ctx->service_name;	break;        case KSSL_SERVER:	string = &kssl_ctx->service_host;	break;        case KSSL_CLIENT:	string = &kssl_ctx->client_princ;	break;        case KSSL_KEYTAB:	string = &kssl_ctx->keytab_file;	break;        default:		return KSSL_CTX_ERR;			break;		}	if (*string)  free(*string);	if (!text)                {		*string = '\0';		return KSSL_CTX_OK;		}	if ((*string = calloc(1, strlen(text) + 1)) == NULL)

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -