Refactored NLA to be self contained.
authorArmin Novak <armin.novak@thincast.com>
Tue, 20 Nov 2018 15:48:59 +0000 (16:48 +0100)
committerArmin Novak <armin.novak@thincast.com>
Wed, 5 Dec 2018 09:55:06 +0000 (10:55 +0100)
libfreerdp/core/nego.c
libfreerdp/core/nla.c
libfreerdp/core/nla.h
libfreerdp/core/rdp.c
libfreerdp/core/transport.c

index ece8a4b..dd663c7 100644 (file)
@@ -1426,7 +1426,7 @@ SEC_WINNT_AUTH_IDENTITY* nego_get_identity(rdpNego* nego)
        if (!nego)
                return NULL;
 
-       return nego->transport->nla->identity;
+       return nla_get_identity(nego->transport->nla);
 }
 
 void nego_free_nla(rdpNego* nego)
index 9a7659d..c146a97 100644 (file)
 
 #define TERMSRV_SPN_PREFIX     "TERMSRV/"
 
+
+struct rdp_nla
+{
+       BOOL server;
+       NLA_STATE state;
+       int sendSeqNum;
+       int recvSeqNum;
+       freerdp* instance;
+       CtxtHandle context;
+       LPTSTR SspiModule;
+       char* SamFile;
+       rdpSettings* settings;
+       rdpTransport* transport;
+       UINT32 cbMaxToken;
+#if defined(UNICODE)
+       SEC_WCHAR* packageName;
+#else
+       SEC_CHAR* packageName;
+#endif
+       UINT32 version;
+       UINT32 peerVersion;
+       UINT32 errorCode;
+       ULONG fContextReq;
+       ULONG pfContextAttr;
+       BOOL haveContext;
+       BOOL haveInputBuffer;
+       BOOL havePubKeyAuth;
+       SECURITY_STATUS status;
+       CredHandle credentials;
+       TimeStamp expiration;
+       PSecPkgInfo pPackageInfo;
+       SecBuffer inputBuffer;
+       SecBuffer outputBuffer;
+       SecBufferDesc inputBufferDesc;
+       SecBufferDesc outputBufferDesc;
+       SecBuffer negoToken;
+       SecBuffer pubKeyAuth;
+       SecBuffer authInfo;
+       SecBuffer ClientNonce;
+       SecBuffer PublicKey;
+       SecBuffer tsCredentials;
+       LPTSTR ServicePrincipalName;
+       SEC_WINNT_AUTH_IDENTITY* identity;
+       PSecurityFunctionTable table;
+       SecPkgContext_Sizes ContextSizes;
+};
+
 static BOOL nla_send(rdpNla* nla);
 static int nla_recv(rdpNla* nla);
 static void nla_buffer_print(rdpNla* nla);
@@ -2387,3 +2434,37 @@ void nla_free(rdpNla* nla)
        nla_identity_free(nla->identity);
        free(nla);
 }
+
+SEC_WINNT_AUTH_IDENTITY* nla_get_identity(rdpNla* nla)
+{
+       if (!nla)
+               return NULL;
+
+       return nla->identity;
+}
+
+NLA_STATE nla_get_state(rdpNla* nla)
+{
+       if (!nla)
+               return NLA_STATE_FINAL;
+
+       return nla->state;
+}
+
+BOOL nla_set_state(rdpNla* nla, NLA_STATE state)
+{
+       if (!nla)
+               return FALSE;
+
+       nla->state = state;
+       return TRUE;
+}
+
+BOOL nla_set_service_principal(rdpNla* nla, LPSTR principal)
+{
+       if (!nla || !principal)
+               return FALSE;
+
+       nla->ServicePrincipalName = principal;
+       return TRUE;
+}
index fcd2ece..2c5a13e 100644 (file)
@@ -47,52 +47,6 @@ enum _NLA_STATE
 };
 typedef enum _NLA_STATE NLA_STATE;
 
-struct rdp_nla
-{
-       BOOL server;
-       NLA_STATE state;
-       int sendSeqNum;
-       int recvSeqNum;
-       freerdp* instance;
-       CtxtHandle context;
-       LPTSTR SspiModule;
-       char* SamFile;
-       rdpSettings* settings;
-       rdpTransport* transport;
-       UINT32 cbMaxToken;
-#if defined(UNICODE)
-       SEC_WCHAR* packageName;
-#else
-       SEC_CHAR* packageName;
-#endif
-       UINT32 version;
-       UINT32 peerVersion;
-       UINT32 errorCode;
-       ULONG fContextReq;
-       ULONG pfContextAttr;
-       BOOL haveContext;
-       BOOL haveInputBuffer;
-       BOOL havePubKeyAuth;
-       SECURITY_STATUS status;
-       CredHandle credentials;
-       TimeStamp expiration;
-       PSecPkgInfo pPackageInfo;
-       SecBuffer inputBuffer;
-       SecBuffer outputBuffer;
-       SecBufferDesc inputBufferDesc;
-       SecBufferDesc outputBufferDesc;
-       SecBuffer negoToken;
-       SecBuffer pubKeyAuth;
-       SecBuffer authInfo;
-       SecBuffer ClientNonce;
-       SecBuffer PublicKey;
-       SecBuffer tsCredentials;
-       LPTSTR ServicePrincipalName;
-       SEC_WINNT_AUTH_IDENTITY* identity;
-       PSecurityFunctionTable table;
-       SecPkgContext_Sizes ContextSizes;
-};
-
 FREERDP_LOCAL int nla_authenticate(rdpNla* nla);
 FREERDP_LOCAL LPTSTR nla_make_spn(const char* ServiceClass,
                                   const char* hostname);
@@ -100,6 +54,13 @@ FREERDP_LOCAL LPTSTR nla_make_spn(const char* ServiceClass,
 FREERDP_LOCAL int nla_client_begin(rdpNla* nla);
 FREERDP_LOCAL int nla_recv_pdu(rdpNla* nla, wStream* s);
 
+FREERDP_LOCAL SEC_WINNT_AUTH_IDENTITY* nla_get_identity(rdpNla* nla);
+
+FREERDP_LOCAL NLA_STATE nla_get_state(rdpNla* nla);
+FREERDP_LOCAL BOOL nla_set_state(rdpNla* nla, NLA_STATE state);
+
+FREERDP_LOCAL BOOL nla_set_service_principal(rdpNla* nla, LPSTR principal);
+
 FREERDP_LOCAL rdpNla* nla_new(freerdp* instance, rdpTransport* transport,
                               rdpSettings* settings);
 FREERDP_LOCAL void nla_free(rdpNla* nla);
index 07492ac..f199fdf 100644 (file)
@@ -1388,7 +1388,7 @@ int rdp_recv_callback(rdpTransport* transport, wStream* s, void* extra)
        switch (rdp->state)
        {
                case CONNECTION_STATE_NLA:
-                       if (rdp->nla->state < NLA_STATE_AUTH_INFO)
+                       if (nla_get_state(rdp->nla) < NLA_STATE_AUTH_INFO)
                        {
                                if (nla_recv_pdu(rdp->nla, s) < 1)
                                {
@@ -1396,7 +1396,7 @@ int rdp_recv_callback(rdpTransport* transport, wStream* s, void* extra)
                                        return -1;
                                }
                        }
-                       else if (rdp->nla->state == NLA_STATE_POST_NEGO)
+                       else if (nla_get_state(rdp->nla) == NLA_STATE_POST_NEGO)
                        {
                                nego_recv(rdp->transport, s, (void*) rdp->nego);
 
@@ -1406,10 +1406,11 @@ int rdp_recv_callback(rdpTransport* transport, wStream* s, void* extra)
                                        return -1;
                                }
 
-                               rdp->nla->state = NLA_STATE_FINAL;
+                               if (!nla_set_state(rdp->nla, NLA_STATE_FINAL))
+                                       return -1;
                        }
 
-                       if (rdp->nla->state == NLA_STATE_AUTH_INFO)
+                       if (nla_get_state(rdp->nla) == NLA_STATE_AUTH_INFO)
                        {
                                transport_set_nla_mode(rdp->transport, FALSE);
 
@@ -1422,15 +1423,18 @@ int rdp_recv_callback(rdpTransport* transport, wStream* s, void* extra)
                                                return -1;
 
                                        nego_send_negotiation_request(rdp->nego);
-                                       rdp->nla->state = NLA_STATE_POST_NEGO;
+
+                                       if (!nla_set_state(rdp->nla, NLA_STATE_POST_NEGO))
+                                               return -1;
                                }
                                else
                                {
-                                       rdp->nla->state = NLA_STATE_FINAL;
+                                       if (!nla_set_state(rdp->nla, NLA_STATE_FINAL))
+                                               return -1;
                                }
                        }
 
-                       if (rdp->nla->state == NLA_STATE_FINAL)
+                       if (nla_get_state(rdp->nla) == NLA_STATE_FINAL)
                        {
                                nla_free(rdp->nla);
                                rdp->nla = NULL;
index 14c6fe2..ee64eb9 100644 (file)
@@ -334,10 +334,8 @@ BOOL transport_connect_nla(rdpTransport* transport)
 
        if (settings->AuthenticationServiceClass)
        {
-               rdp->nla->ServicePrincipalName =
-                   nla_make_spn(settings->AuthenticationServiceClass, settings->ServerHostname);
-
-               if (!rdp->nla->ServicePrincipalName)
+               if (!nla_set_service_principal(rdp->nla, nla_make_spn(settings->AuthenticationServiceClass,
+                                              settings->ServerHostname)))
                        return FALSE;
        }