Hi all, We currently have some issues with loadbalancing with the mstshash cookies. We have a few deployments of haproxy running in various TS farms setup to use mstshash for persistence however we have multiple reports of users ending up with multiple active sessions over separate servers.
On looking at the MS Docs for the x224 Connection Request PDU I see the following (This has since been changed by microsoft due to a support call we have with Microsoft at the moment see end of email for the change) <13> Section 3.2.5.3.1: Microsoft RDP 5.1, 5.2, 6.0, 6.1, 7.0, 7.1, and 8.0 clients always include the cookie field in the X.224 Connection Request PDU if a nonempty username can be retrieved for the current user and the routingToken field is not present (the IDENTIFIER used in the cookie string is the login name of the user truncated to nine characters). Now this is what is what I would expect the client to do, however on running some packet captures this seams to not be true any more (since windows 7 or XP if you install the optional RDP client update) under the following conditions. 1. If you connect with the cached credentials - no Cooke is sent. 2. if you enter the wrong username, try to connect then correct username - previous username is used for hash. We have also seen issues where the wrong password caused the username format to be changed to domain/user in the cookie and caused issues when the domain is longer then 9 characters. Has anyone seen this behaviour before and have any solutions to it? also from microsofts response to our current support call (open for over 3 months so far) we have the following. ------------------------------------------------- As documented in MS-RDPBCGR section 3.2.5.3.1, the routingToken field is optional. The client normally retrieves routing token from the load balancing information (LoadBalanceInfo field) it previously received from the server in the server redirection packet (see RDP_SERVER_REDIRECTION_PACKET, MS-RDPBCGR section 2.2.13.1). If the routing token cannot be provisioned (e.g. because there is no load balancing information available, no scripted cookie or no file input available), the default built-in cookie hash Cookie: mstshash=<IDENTIFIER> is always sent provided that the session’s user name can be retrieved. The root cause is that the server redirection packet was including both LB_TARGET_NET_ADDRESS and LB_LOAD_BALANCE_INFO. In order for the Windows 7 client to send the routingToken, the server needs to set only the LB_LOAD_BALANCE_INFO and also include the LoadBalanceInfo (see references below). The update in Section “2.2.13.1 Server Redirection Packet (RDP_SERVER_REDIRECTION_PACKET)” reflects the correct behavior. 2.2.13.1 Server Redirection Packet (RDP_SERVER_REDIRECTION_PACKET) *http://msdn.microsoft.com/en-us/library/ee443575(v=PROT.10).aspx*<http://msdn.microsoft.com/en-us/library/ee443575%28v=PROT.10%29.aspx> NOTE: this section has been updated, and the change will appear in a future release of the document. LoadBalanceInfoLength (4 bytes): A 32-bit unsigned integer. The length, in bytes, of the LoadBalanceInfo field. LoadBalanceInfo (variable): A variable-length array of bytes containing load balancing information that MUST be treated as opaque data by the client and passed to the server if the LB_TARGET_NET_ADDRESS (0x00000001) flag is not present in the RedirFlags field and a reconnection takes place. See section 3.2.5.3.1 for details on populating the routingToken field of the X.224 Connection Request PDU (section 2.2.1.1). 3.2.5.3.1 Sending X.224 Connection Request PDU *http://msdn.microsoft.com/en-us/library/cc240663(v=PROT.10).aspx*<http://msdn.microsoft.com/en-us/library/cc240663%28v=PROT.10%29.aspx> The routingToken field is optional. If the client is in possession of a routing token, it MUST populate the routingToken field. The primary source of a routing token is the LoadBalanceInfo field of the Server Redirection PDU (see section 2.2.13.1). However other methods, such as scriptable APIs or file input, can be used to provide a client with a routing token before a connection to an RDP server is initiated. For more information about the routing token format, see [MSFT-SDLBTS] "Routing Token Format". The cookie field is optional and MUST NOT be present if the routingToken field is present. NOTE: This Windows behavior note has been updated, and the change will appear in a future release of the document. <13> Section 3.2.5.3.1: Microsoft RDP 5.1, 5.2, 6.0, 6.1, 7.0, 7.1, and 8.0 clients always include the cookie field in the X.224 Connection Request PDU if a nonempty username can be retrieved for the current user and the routingToken field is not present (the IDENTIFIER used in the cookie string is the login name of the user truncated to nine characters). *http://msdn.microsoft.com/en-us/library/aa381177%28VS.85%29.aspx*<http://msdn.microsoft.com/en-us/library/aa381177%28VS.85%29.aspx> Third party website article which I found: *http://www.snakelegs.org/2011/02/06/rdp-cookies-2/*<http://www.snakelegs.org/2011/02/06/rdp-cookies-2/> --------------------------------------------------------------- Could anyone confirm if the above is valid? I notice it says "If the routing token cannot be provisioned (e.g. because there is no load balancing information available, no scripted cookie or no file input available), the default built-in cookie hash Cookie: mstshash=<IDENTIFIER> is always sent provided that the session’s user name can be retrieved." Again this does not seam to be happening as there is no Cookie: mstshash=<IDENTIFIER> in any of the captures. Also the technet article now says the following *"cookie (variable): *An optional and variable-length ANSI character<http://msdn.microsoft.com/en-us/library/ab35aee7-1cf7-42dc-ac74-d0d7f4ca64f7#ansich>string terminated by a 0x0D0A two-byte sequence." This to me says they have changed how it works. can anyone confirm if I am wrong? Kind Regards, Mathew

