InitializeSecurityContext (Schannel) 不改变 BufferType

Posted

技术标签:

【中文标题】InitializeSecurityContext (Schannel) 不改变 BufferType【英文标题】:InitializeSecurityContext (Schannel) not changing BufferType 【发布时间】:2016-10-20 12:32:35 【问题描述】:

所以我有以下代码:

SecBuffer input_buffers[2];
SecBuffer output_buffers[2];
ULONG context_attributes;

/* we need to try and perform the second (next) step of the init */
input_buffers[0].cbBuffer = tls_io_instance->received_byte_count;
input_buffers[0].BufferType = SECBUFFER_TOKEN;
input_buffers[0].pvBuffer = (void*)tls_io_instance->received_bytes;
input_buffers[1].cbBuffer = 0;
input_buffers[1].BufferType = SECBUFFER_EMPTY;
input_buffers[1].pvBuffer = 0;

SecBufferDesc input_buffers_desc;
input_buffers_desc.cBuffers = 2;
input_buffers_desc.pBuffers = input_buffers;
input_buffers_desc.ulVersion = SECBUFFER_VERSION;

output_buffers[0].cbBuffer = 0;
output_buffers[0].BufferType = SECBUFFER_TOKEN;
output_buffers[0].pvBuffer = NULL;
output_buffers[1].cbBuffer = 0;
output_buffers[1].BufferType = SECBUFFER_EMPTY;
output_buffers[1].pvBuffer = 0;

SecBufferDesc output_buffers_desc;
output_buffers_desc.cBuffers = 2;
output_buffers_desc.pBuffers = output_buffers;
output_buffers_desc.ulVersion = SECBUFFER_VERSION;

unsigned long flags = ISC_REQ_EXTENDED_ERROR | ISC_REQ_STREAM | ISC_REQ_ALLOCATE_MEMORY | ISC_REQ_USE_SUPPLIED_CREDS;
SECURITY_STATUS status = InitializeSecurityContext(&tls_io_instance->credential_handle,
                        &tls_io_instance->security_context, (SEC_CHAR*)tls_io_instance->host_name, flags, 0, 0, 
                        &input_buffers_desc, 0,
                        &tls_io_instance->security_context, &output_buffers_desc, &context_attributes, NULL);

问题是,在 Windows 8.1Windows 10 平台上执行此代码后,input_buffers[1].BufferType 设置为 4。如果它在 Windows Server 2012 R2 上执行,input_buffers[1].BufferType 保持 0 (SECBUFFER_MISSING) 并且我最终会出错。有谁知道为什么InitializeSecurityContext (Schannel) function 没有改变 Windows Server 上input_buffers[1] 的类型?

非常感谢您提供的任何帮助。

编辑 1 返回的状态在两个平台上都是相同的 (-2146893032),只是在 Win 8.1/10 上,函数将 input_buffers[1].BufferType 更改为 4。

编辑 2 在 Win 8.1/ 10 上,它进入此案例选项的 else 分支,在 Win Server 2012 R2 中,它进入 if 分支。在所有平台上,状态设置为 SEC_E_INCOMPLETE_MESSAGE (-2146893032)

   switch (status)
            
            case SEC_E_INCOMPLETE_MESSAGE:
                if (input_buffers[1].BufferType != SECBUFFER_MISSING)
                
                    tls_io_instance->tlsio_state = TLSIO_STATE_ERROR;
                    if (tls_io_instance->on_io_open_complete != NULL)
                    
                        tls_io_instance->on_io_open_complete(tls_io_instance->open_callback_context, IO_OPEN_ERROR);
                    
                
                else
                
                    tls_io_instance->needed_bytes = input_buffers[1].cbBuffer;
                    tls_io_instance->consumed_bytes += tls_io_instance->needed_bytes;
                    if (resize_receive_buffer(tls_io_instance, tls_io_instance->received_byte_count + tls_io_instance->needed_bytes) != 0)
                    
                        tls_io_instance->tlsio_state = TLSIO_STATE_ERROR;
                        if (tls_io_instance->on_io_open_complete != NULL)
                        
                            tls_io_instance->on_io_open_complete(tls_io_instance->open_callback_context, IO_OPEN_ERROR);
                        
                    
                

【问题讨论】:

这个问题导致了这个***.com/questions/40133998/… 会不会是您引用的服务器没有安装相关的子项目?即这些项目:azure-uamqp-cazure-c-shared-utility 我在另一边引用 Azure 事件中心,因为他们为客户制作了 library,我猜他们拥有它。无论哪种方式,它的应用程序和相同的代码,只是在 Windows 8.1/10 上执行时,它向事件中心发送消息,但在 Windows Server 2012 R2 上执行时,它失败并关闭套接字 根据文档,当返回 SEC_E_INCOMPLETE_MESSAGE 时,BufferType 成员应该设置为 SECBUFFER_MISSING。您确定调用在 Win8.1/10 平台上返回 SEC_E_INCOMPLETE_MESSAGE 吗? 【参考方案1】:

好的,所以我联系了创建者,看来这是他们实用程序库代码中的一个错误,他们在 utility library 的开发人员分支中修复了它,他们正在测试它。谢谢大家的回复!

【讨论】:

以上是关于InitializeSecurityContext (Schannel) 不改变 BufferType的主要内容,如果未能解决你的问题,请参考以下文章

schannel: next InitializeSecurityContext failed: SEC_E_ILLEGAL_MESSAGE (0x80090326)

如何使用参数(通过 HTTP)向 NTLM 进行身份验证?