One of the benefits of a third-party add-on product to Terminal
Services such as Citrix MetaFrame Presentation Server is published
applications with seamless windows. In fact the default setting for MPS
3.0 is to only allow users to access remote servers via published
Most people use seamless windows every day without actually knowing
how the technology works. This article will explain how these technical
components work and how you can fix seamless windows problems by
focusing on Windows 2000/2003 up through MPS 3.0. Citrix Presentation
Server 4.0 will work a bit differently, and we’ll discuss that in a
How does seamless windows work?
Applications with seamless windows require components on the server
side as well as the client side. Modern versions of the Win32 ICA
clients have the seamless components built into the core client engine
(wfica32.exe). On the server side the bulk of the seamless engine
resides in an executable called wfshell.exe (although it also depends in
part on ctxnotify.dll and semain20.dll).
The server side and client side components communicate with each
other via a virtual channel used exclusively for seamless windows data
communication. This virtual channel is used for window events (sizing,
location, etc.), for starting additional published applications, and so
The server’s seamless engine is an executable called wfshell.exe.
WFShell is started in each session at logon via CmStart.exe. (CmStart is
an executable that’s launched via the server’s AppSetup registry value.
For more information about this value check out my previous article “Understanding the Citrix MetaFrame Logon and Logoff Process.”)
WFShell.exe is responsible for a lot of stuff, including:
- Launching published applications
- Client printer autocreation
- Session virtual channels
- Session sharing
- SpeedScreen / SpeedScreen Browser Acceleration
- Content redirection
- Clipboard mapping
The settings for the server’s WFShell seamless engine are stored in the registry hive
and read every time WFShell is launched. (i.e they’re read every time a new session starts.)
When establishing a connection to a seamless application, the ICA
client sends information about its desktop to the server. This
information includes things like client metrics, display area, color
depth, etc. The server needs this information so that it can (for
example) know when you move a window out of the visible range.
Understanding Session Sharing
One of the behaviors of Citrix that a lot of people don’t know about
is something called “session sharing.” What this means is that when a
user starts a published application on a Citrix server to which they
already have a seamless connection to another application, the second
application “shares” the session of the first. (This can be tricky at
times because it means that a logon script will not be run for the
second application since the user is already logged in to the session
that it’s sharing.)
To launch the second application, the ICA client engine sends the
request to the server via the seamless windows virtual channel and the
WFShell (ctxnotify) starts the application on the server within the same
client session. If needed, session sharing can be disabled by setting
an exception flag (more on exception flags below). You can also check
out this Citrix knowledgebase article that fully explains session
Since both seamless applications share the same ICA connection, session sharing is only possible when:
- The second application has been published on the server where the first application’s session is running
- The second application’s color depth is equal to or lower than
the first application’s color depth. (See “There is no Session-Sharing
if Subsequent Sessions Have Higher Depths” CTX127702 for more details.)
- The second application’s sound quality is equal or lower then the first seamless application’s.
- The second application’s encryption level is the same as the first application.
If you want to make use of session sharing, an easy way to do it is
to use the copy (F8) function within the CMC to create additional
published applications. This will ensure that all your applications have
the same settings. (Of course particular sessions could have different
settings via policies, but that’s a whole other issue.)
Using Seamless Exception Flags to alter Application behavior
had to implement a lot of “tricks” to get seamless windows to work in
MetaFrame. Unfortunately not every application in the world is
programmed in the same way or using the same development tools. To
address this Citrix had to add support for certain non-standard window
behavior of applications.
Applications that don’t perform quite right in seamless windows
environments can be dealt with using the Citrix Seamless Windows
exception flags that are configured in the registry of the Presentation
Server. There are currently 15 global and 7 application-specific flags
that can be set in whatever combination is needed to make a particular
application perform via seamless windows in a way that you want. (See
the PDF attached to this article for more information about settings
that can be changed. This PDF is my extended version of the Citrix
knowledge base article “Seamless Exception Registry Flags – CTX101644”)
Figuring out exactly which exception flag and options you need can be
tricky. You typically have to figure out the window’s ClassName. Citrix
describes this process, although it uses a utility from Microsoft
called SPY++ that you can only get with Visual Studio. You can also use a
free replacement tool called WinSpector. You can find this great utility and many others in my 4GEResource Kit at http://www.citrix4ge.de/tipps/4gereskit.htm.
So just what kind of things can you change with these exception keys?
Well, for example, Borland / Delphi applications might use a so called
“transparent window” which will have issues with the taskbar icon. If
so, try the following registry key:
Value Name: ClassName
Value Type: REG_SZ
Value Name: Type
Value Type: REG_DWORD
Of course this is just an example, but you can change all sorts of things here. (Again, see the attached PDF for a full list.)
Seamless Application Termination
When ending a seamless application, the client engine sends the
request to the server. WFShell terminates the applications that are
running on the server and the ICA client engine closes the window(s).
Unfortunately due to additional programs that have been started or
issues with WFShell, a server session will sometimes remain active on
the server. Even though this is not a “Citrix” problem per se, Citrix
did add a special seamless exception flag (LogoffCheckSysModules) to
terminate those additional programs that get “stuck” when a session
attempts to unload.
If this is something that you experience in your environment then
you’ll have to figure out which process prohibits the graceful session
logoff from the server before you can set any registry keys. To do this,
use the CMC to open the session properties of the stuck session and
terminate the processes one-by-one until a graceful logoff occurs.
Once you figure out which process frees up the logoff (let’s say it’s
“BadApp.exe”) think about whether you really need that executable. If
not, then delete it or uninstall the application. If the executable is
important then add the following registry key:
Value Name: LogoffCheckSysModules
Value Type: REG_SZ
Enter the list of executable names with a comma and NO spaces between them,
for example: App1.exe,app2.exe,app3.exe
The Citrix article CTX891671 describes in more detail the logoff misbehaviour.
Seamless Engine Registry Changes between Windows 2000 and 2003
As companies migrate to Windows Server 2003, some admins have tried
to cut corners by copying the old Windows 2000-based Citrix server’s
ica-tcp registry hive (HKLM\SYSTEM\CurrentControlSet\Control\Terminal
Server\WinStations\ICA-tcp) to their Windows 2003 servers.
Be aware, this procedure will break the seamless engine!
Normally the Windows 2000 ICA Winstation Driver Flag (WdFlag) has a
value of 0x00000e (at least a low value). Now if the Windows 2003 ICA
WdFlag has a value below 0x000048 the seamless engine will break and you
will only get non-seamless sessions. Recreating the ICA listener will
reset all the ica-tcp values to their defaults and solve the issue.