We’ve been using the NX Terminal Server (version 6.3.6) product for a few months. When we reach about 1,5k sessions the terminal server fails assigning new sessions for new users.

Because I can’t play with the productive environment I had to figure out how to make a «stress test» similar enough to replicate the issue by generating multiple sessions and logins with one NX client to the terminal server. In this article I’ll explain how you could achieve a similar task.

Searching on google the closest thing I’d found was benchmark tests on an NX environment. Nothing was explicit but its indications were enough to have an approach.

Using guest accounts

I must be clear with this: Guest accounts in multinode environment do not work at this moment! you can check that link to see if that feature is corrected in newer versions (yes it was fixed in version 6.5.6), the problem is that guest accounts are «logged in» but the login process is never completed. That means the sessions and guest users are created but you will never get a desktop as guest user on a multinode environment.

But, for my particular needs it was enough, because I just wanted to generate multiple sessions and it was happening, so here we go with it, you can modify the template to use other kind of users with passwords or even private keys.

Prepare the template

You’ll need a template to automate the task. Here you have a copy of my template with guest sessions enabled, do not forget to modify the value in <option key=»Server host» value=»myserverofnomachine.domain» /> with your own NX server.

<!DOCTYPE NXClientSettings>
<NXClientSettings version="1.6" application="nxclient" >
 <group name="Advanced" >
  <option key="Disable deferred updates" value="false" />
  <option key="Grab keyboard input" value="" />
  <option key="Grab mouse input" value="" />
  <option key="Enable remote cursor tracking" value="" />
  <option key="Enable HTTP proxy" value="false" />
  <option key="HTTP proxy host" value="" />
  <option key="HTTP proxy port" value="8080" />
  <option key="HTTP proxy password" value="EMPTY_PASSWORD" />
  <option key="Remember HTTP proxy password" value="false" />
  <option key="HTTP proxy username" value="" />
  <option key="Emulate middle mouse button" value="" />
  <option key="Use TOR for SOCKS proxy connections" value="false" />
  <option key="Use URL for automatic proxy configuration" value="false" />
  <option key="Manual proxy configuration type" value="http" />
  <option key="Proxy configuration mode" value="manual" />
  <option key="Automatic proxy configuration URL" value="" />
  <option key="Enable SSL encryption" value="true" />
  <option key="Disable ZLIB stream compression" value="false" />
  <option key="Enable response time optimisations" value="false" />
 </group>
 <group name="Environment" >
  <option key="Use font server" value="false" />
  <option key="Font server host" value="" />
  <option key="Font server port" value="7100" />
 </group>
 <group name="General" >
  <option key="XAgent encoding" value="true" />
  <option key="Enable session auto-resize" value="false" />
  <option key="Connection service" value="nx" />
  <option key="View a specific monitor among available monitors" value="0" />
  <option key="Command line" value="" />
  <option key="Use custom server" value="false" />
  <option key="Custom server command" value="/etc/NX/nxserver" />
  <option key="Custom Unix Desktop" value="console" />
  <option key="Use default image encoding" value="0" />
  <option key="NoMachine daemon port" value="4000" />
  <option key="Connect to this node when manual selection is enabled" value="" />
  <option key="Connect to this server when manual selection is enabled" value="" />
  <option key="Desktop" value="" />
  <option key="Disable SHM" value="false" />
  <option key="Disable emulate shared pixmaps" value="false" />
  <option key="Use render" value="true" />
  <option key="Last connection time" value="1550517531" />
  <option key="Link quality" value="5" />
  <option key="Link speed" value="adsl" />
  <option key="Platform of the last connection" value="Linux" />
  <option key="Session resize mode" value="viewport" />
  <option key="Resize the remote screen to the local geometry" value="true" />
  <option key="Resolution" value="" />
  <option key="Remember session window size and position" value="" />
  <option key="Remember password" value="false" />
  <option key="Remember username" value="true" />
  <option key="Session screenshot" value="" />
  <option key="Server hardware" value="Xen HVM domU" />
  <option key="Server host" value="myserverofnomachine.domain" />
  <option key="Server port" value="22" />
  <option key="Server product" value="Enterprise Terminal Server Subscription" />
  <option key="Session" value="" />
  <option key="Show remote audio alert message" value="true" />
  <option key="Show remote display resize message" value="true" />
  <option key="Use taint" value="true" />
  <option key="Use UDP communication for multimedia data" value="true" />
  <option key="Virtual desktop" value="true" />
  <option key="Session window geometry" value="" />
  <option key="Session window state" value="normal" />
  <option key="xdm mode" value="" />
  <option key="xdm broadcast port" value="177" />
  <option key="xdm list host" value="localhost" />
  <option key="xdm list port" value="177" />
  <option key="xdm query host" value="localhost" />
  <option key="xdm query port" value="177" />
  <option key="Use custom resolution" value="false" />
  <option key="Resolution width" value="" />
  <option key="Resolution height" value="" />
 </group>
 <group name="Login" >
  <option key="Alternate NX Key" value="" />
  <option key="Forward SSH authentication" value="false" />
  <option key="Guest Mode" value="true" />
  <option key="Guest password" value="" />
  <option key="Guest username" value="" />
  <option key="Guest server" value="" />
  <option key="Server authentication method" value="system" />
  <option key="Auth" value="" />
  <option key="User" value="" />
  <option key="NX login method" value="password" />
  <option key="Private key for NX authentication" value="" />
  <option key="Use alternate smart card module" value="false" />
  <option key="Smart card authentication module" value="" />
  <option key="Private key" value="" />
  <option key="Public Key" value="" />
  <option key="System auth" value="EMPTY_PASSWORD" />
  <option key="Two-factor authentication password" value="EMPTY_PASSWORD" />
  <option key="Remember NoMachine password" value="false" />
  <option key="Remember two-factor authentication password" value="false" />
  <option key="Imported private key for NX authentication" value="" />
  <option key="Use imported private key for NX authentication" value="false" />
  <option key="Imported private key" value="" />
  <option key="Use imported private key" value="false" />
  <option key="System login method" value="password" />
  <option key="Use alternate NX Key" value="false" />
  <option key="GSSAPI subsystem for the kerberos authentication" value="kerberos" />
  <option key="Kerberos key exchange to identify server host" value="false" />
  <option key="DNS translation when passing server to Kerberos library" value="false" />
 </group>
 <group name="Images" >
  <option key="Disable network-adaptive quality" value="false" />
  <option key="Disable backingstore" value="false" />
  <option key="Disable composite" value="false" />
  <option key="Disable image post-processing" value="false" />
  <option key="Disable frame buffering on decoding" value="false" />
  <option key="Disable lossless display refinement" value="false" />
  <option key="Disable multi-pass display encoding" value="false" />
  <option key="E-reader display update policy" value="false" />
  <option key="Video frame rate for display server" value="30" />
  <option key="Stream downsampling factor" value="0" />
  <option key="Image Compression Type" value="" />
  <option key="Image encoding quality" value="5" />
  <option key="JPEG Quality" value="" />
  <option key="RDP Image Encoding" value="" />
  <option key="RDP JPEG Quality" value="" />
  <option key="Request a specific frame rate" value="false" />
  <option key="Video encoding quality" value="5" />
  <option key="VNC images compression" value="" />
  <option key="VNC JPEG Quality" value="" />
 </group>
 <group name="Services" >
  <option key="Output audio device" value="autodetect" />
  <option key="Output audio quality" value="5" />
  <option key="Audio" value="true" />
  <option key="IPPPrinting" value="true" />
  <option key="Enable devices sharing" value="true" />
  <option key="Shares" value="true" />
  <option key="Mute audio of the remote physical desktop" value="true" />
  <option key="Input voice device" value="autodetect" />
  <option key="Input voice quality" value="5" />
 </group>
 <group name="VNC Session" >
  <option key="Display" value=":0" />
  <option key="Password" value="EMPTY_PASSWORD" />
  <option key="Remember login credentials" value="false" />
  <option key="Remember" value="false" />
  <option key="Server" value="" />
 </group>
 <group name="Windows Session" >
  <option key="Application" value="" />
  <option key="Authentication" value="2" />
  <option key="Color Depth" value="" />
  <option key="Domain" value="" />
  <option key="Image Cache" value="" />
  <option key="Password" value="EMPTY_PASSWORD" />
  <option key="Remember login credentials" value="false" />
  <option key="Remember" value="false" />
  <option key="Run application" value="false" />
  <option key="Server" value="" />
  <option key="User" value="" />
 </group>
 <group name="Remote Session" >
  <option key="Host" value="" />
  <option key="Port" value="" />
  <option key="Username" value="" />
  <option key="Password" value="EMPTY_PASSWORD" />
  <option key="Remember login credentials" value="false" />
  <option key="Fingerprint" value="" />
 </group>
</NXClientSettings>

Then, we’ll need multiple templates to generate multiple connections (it doesn’t matter if you use user/password/private key or guest accounts) in case of guest accounts the client will place a user and encrypted password on each template, remember each password will be encrypted in this way.

To generate multiple templates you could execute:

for i in {1..100}; do cp original_template.nxs my_template_$i.nxs; done

This will just copy the original template provided before into 100 new templates «my_template_1, etc…».

Now that we have so many templates it’s time to generate many connections, we can achieve that in this way:

for i in {1..100}; do (/bin/bash /usr/NX/bin/nxplayer --session my_template_$i.nxs --exit --hide &) ; sleep 7; done
  • The previous command do a loop from 1 to 100
  • Then executes /bin/bash to span a new subprocess each time (otherwise you should wait to close the current connection until the next is generated and we want multiple sessions one after another).
  • The sleep 7 just makes you wait 7 seconds after calling each !m session, you could directly remove this if you want the consecutive logins faster.

The result, many instances of the NX client spawned:

No machine multiple sessions generated.

No machine multiple sessions generated.

At server level we can monitor the sessions being created with:

watch -n1 nxserver --list
NX> 127 Available sessions:

Display Username  Remote IP     Session ID                       Node                     
------- --------- ------------- -------------------------------- ------------------------ 
        guest0200 172.10.10.3 051C29F106C5E621DEC9 NOMACHINENODEX:4000
        guest0151 172.10.10.3 33F13BA5C7787DCFE683 NOMACHINENODEX:4000
        guest0150 172.10.10.3 EE2DBECB9371348DC8E2 NOMACHINENODEX:4000
        guest0149 172.10.10.3 C7F22639F0F175A3C1B4 NOMACHINENODEX:4000
        guest0199 172.10.10.3 89AAC567B282A0A82045 NOMACHINENODEX:4000
        guest0198 172.10.10.3 C77E69E21176EB096C56 NOMACHINENODEX:4000
        guest0197 172.10.10.3 02ED5FDEE201B0F50F9F NOMACHINENODEX:4000
        guest0196 172.10.10.3 AB6E37B742C53C96059D NOMACHINENODEX:4000
        guest0195 172.10.10.3 429161E36DCF69FD8448 NOMACHINENODEX:4000
        guest0194 172.10.10.3 D2107B3E5F5DDBCC244E NOMACHINENODEX:4000
        guest0193 172.10.10.3 05BACB468E0AE8435AB8 NOMACHINENODEX:4000
        guest0192 172.10.10.3 E5CAA9E80721BC4A5F3D NOMACHINENODEX:4000
        guest0191 172.10.10.3 BA14BDCD7961FFC39CCB NOMACHINENODEX:4000
        guest0190 172.10.10.3 217B828AF28AF51F6C7C NOMACHINENODEX:4000
        guest0189 172.10.10.3 1A811325A620DCD23F69 NOMACHINENODEX:4000
        guest0188 172.10.10.3 7DED22DD640DCDA285C0 NOMACHINENODEX:4000
        guest0187 172.10.10.3 A0C301B26A5C003022E1 NOMACHINENODEX:4000

The guest name will be increased each time you generate new guest connections.

It was all fun and games until the system started to fail:

2019-02-19 13:35:14 412.025 11548 NXSERVER WARNING! User guest0200 doesn't exist in system.
2019-02-19 13:35:14 412.148 11548 NXSERVER WARNING! NXLogin: Cannot retrieve absolute username for user: guest0200.
2019-02-19 13:35:14 413.717 11548 NXSERVER WARNING! User guest0200 doesn't exist in system.
2019-02-19 13:35:14 415.397 11548 NXSERVER Previous message repeated 1 time
2019-02-19 13:35:14 415.473 11548 NXSERVER WARNING! NXLogin: Cannot retrieve absolute username for user: guest0200.
2019-02-19 13:35:14 417.252 11548 NXSERVER WARNING! User guest0200 doesn't exist in system.
2019-02-19 13:35:15 860.578 11579 NXSERVER ERROR! Timeout on session id '4E0B261668DA0C1F04C1FEB49FE9D779': session was registered 125sec. ago, but it is still in status: Starting
2019-02-19 13:35:16 143.357 11548 NXSERVER User 'guest0200' logged in from '76.252.78.188' using authentication method NX-password.
2019-02-19 13:35:21 782.025 11631 NXSERVER WARNING! Cannot assign guest account.
2019-02-19 13:35:28 588.461 11658 NXSERVER WARNING! Cannot assign guest account.
2019-02-19 13:35:35 701.338 11676 NXSERVER WARNING! Cannot assign guest account.
2019-02-19 13:35:42 690.312 11698 NXSERVER WARNING! Cannot assign guest account.
2019-02-19 13:35:49 682.901 11728 NXSERVER WARNING! Cannot assign guest account.
2019-02-19 13:35:56 676.539 11758 NXSERVER WARNING! Cannot assign guest account.
2019-02-19 13:36:04 069.117 11784 NXSERVER WARNING! Cannot assign guest account.
2019-02-19 13:36:10 781.390 11803 NXSERVER WARNING! Cannot assign guest account.
2019-02-19 13:40:37 385.497 13957 NXSERVER WARNING! Cannot assign guest account.
2019-02-19 13:40:44 126.983 14027 NXSERVER WARNING! Cannot assign guest account.
2019-02-19 13:40:51 126.448 14101 NXSERVER WARNING! Cannot assign guest account.
2019-02-19 13:43:10 903.743 15110 NXSERVER WARNING! Cannot write to FD#1.
2019-02-19 13:43:10 903.860 15110 NXSERVER WARNING! Error is: 32, 'Broken pipe'.

So maybe isn’t completely similar to my productive environment but its useful as reference when I’m allowed to do something similar on production.