将GSS-SPNEGO与GSS_krb5_import_cred一起使用
我试图实现为我的应用程序请求TGT的编程逻辑,因此在通过GSSAPI和GSS-SPNEGO机制对LDAP服务器进行身份验证之前,不需要从命令行调用将GSS-SPNEGO与GSS_krb5_import_cred一起使用,c,ldap,kerberos,gssapi,C,Ldap,Kerberos,Gssapi,我试图实现为我的应用程序请求TGT的编程逻辑,因此在通过GSSAPI和GSS-SPNEGO机制对LDAP服务器进行身份验证之前,不需要从命令行调用kinit 我创建一个内存ccache,请求一个带有用户名和密码的TGT,然后使用gss\u krb5\u import\u cred导入凭据。在启动身份验证之前,为LDAP结构设置GSSAPI上下文 下面的示例代码在GSSAPI中运行良好,但当我尝试将机制更改为GSS-SPNEGO时,我收到一个本地LDAP错误(-2),并显示以下消息: SASL(-
kinit
我创建一个内存ccache,请求一个带有用户名和密码的TGT,然后使用gss\u krb5\u import\u cred导入凭据。在启动身份验证之前,为LDAP结构设置GSSAPI上下文
下面的示例代码在GSSAPI中运行良好,但当我尝试将机制更改为GSS-SPNEGO时,我收到一个本地LDAP错误(-2),并显示以下消息:
SASL(-1):一般故障:GSSAPI错误:未指定的GSS故障。次要代码可能提供更多信息(SPNEGO无法找到协商机制)
int create_krb5_cred(krb5_context ctx,char*realm,char*user,
字符*密码,krb5_ccache*ccache,gss_cred_id_t*gsscred){
int rc=0,minor_stat=0;
int len=0;
const char*cname=NULL;
krb5_get_init_creds_opt*cred_opt;
krb5_信条;
krb5_principal princ=NULL;
if(realm==NULL | | user==NULL | | password==NULL)返回-1;
rc=krb5_cc_new_unique(ctx,“内存”,NULL,ccache);
如果(rc!=0)转到清除;
len=strlen(领域);
rc=krb5_build_principal(ctx,&princ,len,realm,user,NULL);
如果(rc!=0)转到清除;
rc=krb5_cc_初始化(ctx,*ccache,princ);
如果(rc!=0)转到清除;
rc=krb5_get_init_creds_opt_alloc(ctx和cred_opt);
如果(rc!=0)转到清除;
rc=krb5_get_init_creds_password(ctx,&creds,princ,password,0,NULL,0,NULL,NULL);
如果(rc!=0)转到清除;
rc=krb5_cc_商店_cred(ctx、*ccache和cred);
如果(rc!=0)转到清除;
cname=krb5_cc_get_name(ctx,*ccache);
如果(cname==NULL)转到清除;
rc=gss_krb5_ccache_name(&minor_stat,cname,NULL);
如果(rc!=0)转到清除;
rc=gss_krb5_import_cred(&minor_stat,*ccache,princ,0,gsscred);
清楚:
if(princ!=NULL)krb5_free_principal(ctx,princ);
返回rc;
}
int remove_krb5_cred(krb5_context ctx,krb5_ccache ccache,gss_cred_id_t*gsscred){
int rc=0;
rc=gss\u发布\u凭证(空,gsscred);
如果(rc!=0)返回rc;
rc=krb5_cc_destroy(ctx,ccache);
krb5_自由上下文(ctx);
返回rc;
}
内部主(空){
int rc=0;
krb5_-ctx;
krb5_ccache ccache;
gss_cred_id_t gsscred=NULL;
rc=krb5_init_上下文(&ctx);
创建_krb5_cred(ctx,“EXAMPLE.ORG”、“testuser”、“secret”、&ccache和&gsscred);
LDAP*ld=NULL;
const int version=LDAP_VERSION3;
void*默认值=NULL;
ldap\u初始化(&ld)ldap://example.org");
ldap_set_选项(ld、ldap_OPT_协议版本和版本);
/*使用“interact”函数设置凭据并处理SASL绑定
(设置新的GSS上下文)此处未披露*/
rc=ldap\u sasl\u interactive\u bind\s(ld,NULL,“GSSAPI”,NULL,NULL,0,interactive,默认值);
printf(“连接0x%x\n”,rc);
移除CRB5 cred(ctx、ccache和gsscred);
结构berval*authzid;
rc=ldap\u whoami\u s(ld和authzid,NULL,NULL);
printf(“RC%d%s\n\n”,RC,authzid->bv_val);
}
旧论坛帖子建议未为导入的凭据设置SPNEGO oid,因此LDAP将在身份验证期间忽略它
我曾尝试使用gss\u acquire\u cred
函数而不是gss\u krb5\u import\u cred
,但我没有成功地用它接收到TGT(即使是GSSAPI)
欢迎提出任何关于如何通过GSSAPI和GSS-SPNEGO成功认证的想法
更新:我已经设法将gss\u acquire\u cred
与GSSAPI和gss-SPNEGO一起使用,但我不得不使用基于文件的凭证缓存,而不是基于内存的凭证缓存 要做到这一点,需要采取以下几项措施:
获得常规TGT
确保Cyrus SASL是针对MIT Kerberos正确编译的。您可以使用pluginviewer
根据Cyrus SASL正确编译OpenLDAP
使用ldapsearch
测试您的设置,以确保Kerberos实际工作
如果一切顺利,请继续:
使用带有密码的公共功能
现在,使用交互式绑定准备LDAP
句柄,其他操作都不起作用
这个句柄可以通过auth传递给Cyrus SASL,Cyrus SASL希望它采用机制的格式
现在,您需要使用指针和sizeof
将您的gss\u cred\t
传递到berval
结构
Cyrus SASL会将其拾取并传递给GSS上下文
不幸的是,OpenLDAP和Cyrus SASL都是可怕的文档。我怎么知道它会起作用?我阅读了两者的源代码,以理解并利用该用例
从读取头文件开始,您将得到一个结果。如果卡住了,请重新询问