加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 综合聚焦 > 服务器 > Windows > 正文

windows – 如何正确调用LsaLogonUser进行交互式登录?

发布时间:2020-12-14 01:55:27 所属栏目:Windows 来源:网络整理
导读:我正在尝试使用LsaLogonUser创建交互式登录会话,但它始终返回STATUS_INVALID_INFO_CLASS(0xc0000003).从我在网上搜索中发现的内容来看,KERB_INTERACTIVE_LOGON结构的内存布局很棘手,但我很确定我已经做到了. 我还尝试使用MSV1.0而不是Kerberos,MSV1_0_INTERA
我正在尝试使用LsaLogonUser创建交互式登录会话,但它始终返回STATUS_INVALID_INFO_CLASS(0xc0000003).从我在网上搜索中发现的内容来看,KERB_INTERACTIVE_LOGON结构的内存布局很棘手,但我很确定我已经做到了.

我还尝试使用MSV1.0而不是Kerberos,MSV1_0_INTERACTIVE_LOGON用于身份验证结构,MSV1_0_PACKAGE_NAME用作包名,但是使用STATUS_BAD_VALIDATION_CLASS(0xc00000a7)失败.

谁能告诉我这里做错了什么?这是代码,大部分错误处理都被剥离了.显然,这不是生产质量;我只想尝试一个工作样本.

// see below for definitions of these
size_t wcsByteLen( const wchar_t* str );
void InitUnicodeString( UNICODE_STRING& str,const wchar_t* value,BYTE* buffer,size_t& offset );

int main( int argc,char * argv[] )
{
    // connect to the LSA
    HANDLE lsa;
    LsaConnectUntrusted( &lsa );

    const wchar_t* domain = L"mydomain";
    const wchar_t* user = L"someuser";
    const wchar_t* password = L"scaryplaintextpassword";

    // prepare the authentication info
    ULONG authInfoSize = sizeof(KERB_INTERACTIVE_LOGON) +
     wcsByteLen( domain ) + wcsByteLen( user ) + wcsByteLen( password );
    BYTE* authInfoBuf = new BYTE[authInfoSize];
    KERB_INTERACTIVE_LOGON* authInfo = (KERB_INTERACTIVE_LOGON*)authInfoBuf;
    authInfo->MessageType = KerbInteractiveLogon;
    size_t offset = sizeof(KERB_INTERACTIVE_LOGON);
    InitUnicodeString( authInfo->LogonDomainName,domain,authInfoBuf,offset );
    InitUnicodeString( authInfo->UserName,user,offset );
    InitUnicodeString( authInfo->Password,password,offset );

    // find the Kerberos security package
    char packageNameRaw[] = MICROSOFT_KERBEROS_NAME_A;
    LSA_STRING packageName;
    packageName.Buffer = packageNameRaw;
    packageName.Length = packageName.MaximumLength = (USHORT)strlen( packageName.Buffer );
    ULONG packageId;
    LsaLookupAuthenticationPackage( lsa,&packageName,&packageId );

    // create a dummy origin and token source
    LSA_STRING origin = {};
    origin.Buffer = _strdup( "TestAppFoo" );
    origin.Length = (USHORT)strlen( origin.Buffer );
    origin.MaximumLength = origin.Length;
    TOKEN_SOURCE source = {};
    strcpy( source.SourceName,"foobar" );
    AllocateLocallyUniqueId( &source.SourceIdentifier );

    void* profileBuffer;
    DWORD profileBufLen;
    LUID luid;
    HANDLE token;
    QUOTA_LIMITS qlimits;
    NTSTATUS subStatus;
    NTSTATUS status = LsaLogonUser( lsa,&origin,Interactive,packageId,&authInfo,authInfoSize,&source,&profileBuffer,&profileBufLen,&luid,&token,&qlimits,&subStatus );
    if( status != ERROR_SUCCESS )
    {
        ULONG err = LsaNtStatusToWinError( status );
        printf( "LsaLogonUser failed: %xn",status );
        return 1;
    }
}

size_t wcsByteLen( const wchar_t* str )
{
    return wcslen( str ) * sizeof(wchar_t);
}

void InitUnicodeString( UNICODE_STRING& str,size_t& offset )
{
    size_t size = wcsByteLen( value );
    str.Length = str.MaximumLength = (USHORT)size;
    str.Buffer = (PWSTR)(buffer + offset);
    memcpy( str.Buffer,value,size );
    offset += size;
}

解决方法

你把其中一个参数搞砸了LsaLogonUser();而不是& authInfo你应该只传递authInfo.发生在每个人:)

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读