I think I have found the cause of this problem which does appear to be a Windows 8 bug, feature or oddity, fortunately there does appear to be a fairly simply workaround. I ended up writing some test code using the Win32 WNet API to see if I could work out what was happening. All the following assumes that you are running with elevated or Admin privileges, the WNet functions appear to behave differently when running with user privileges.
If you call WNetAddConnection2 with NULL for the username and password arguments then most of the time the server is sent the username in the form ‘<node>\<local_username>’, however on some occasions the username is sent in the ‘MicrosoftAccount\<live_id_username>’ form. I can reproduce this when I start my code from the Windows Task scheduler at login, which is the same as I am seeing with SyncBack. If you call WNetGetUser the username returned is the Microsoft Account username, even when the local account username is used to successfully login to the server.
The workaround to this problem is not to call WNetAddConnection2 with a NULL argument for the username, instead get the username using some other mechanism such GetUserNameEx to get the local account username (e.g. ‘<node>\<local_username>’) and use this as the username argument to WNetAddConnection2.
The following is some of the observations I have made while investigate this problem.
The connections created by WNetAddConnection2 appear to be session wide and therefore shared by all processes and applications running with that session. If you call WNetAddConnection2 and there is already a connection created by a different application then it will share this connection and if you call WNetGetUser you will get the username used when the other application created the new connection was created.
If you call WNetCancelConnection2 on a connection that is shared between two different applications then it disconnects not just the connection for the application calling the function but it will also disconnect the other application (I have seen this with SyncBack disconnecting my test code). When you reconnect (using WNetAddConnection2 with NULL arguments) the username returned by WNetGetUser is still the username that was used by the other application when it created the connection, so it appears that username is possibly cached somewhere within the Windows Networking code. My server ignores the node/domain part of the username so I currently have SyncBack set to use subtlety different, but valid, usernames to work out what is going on.
Because calling WNetCancelConnection2 disconnects all applications it would appear to some you want to avoid, even if you know that you created a connection you cannot know if another application has started to use it. It is possible that this is the cause of Windows Explorer showing mapped drives as disconnected and other issues that I have being seeing. Also the connection only appears to be within Windows, it does not necessary cause the actually cause this connection to the server to be disconnected.
I suspect that somehow some other task run by WTS at login in the same session may be causing the problem. If I configure WTS so the test code runs in session 0 the problem does not seem to occur so this does seem to be a likely cause. This is only a suspicion and I have no proof of this and this particular system hasn’t got a lot of applications installed so it is a bit mystery if this is the case.
I can supply the test code and some of the output if this help.
Andrew.
If you call WNetAddConnection2 with NULL for the username and password arguments then most of the time the server is sent the username in the form ‘<node>\<local_username>’, however on some occasions the username is sent in the ‘MicrosoftAccount\<live_id_username>’ form. I can reproduce this when I start my code from the Windows Task scheduler at login, which is the same as I am seeing with SyncBack. If you call WNetGetUser the username returned is the Microsoft Account username, even when the local account username is used to successfully login to the server.
The workaround to this problem is not to call WNetAddConnection2 with a NULL argument for the username, instead get the username using some other mechanism such GetUserNameEx to get the local account username (e.g. ‘<node>\<local_username>’) and use this as the username argument to WNetAddConnection2.
The following is some of the observations I have made while investigate this problem.
The connections created by WNetAddConnection2 appear to be session wide and therefore shared by all processes and applications running with that session. If you call WNetAddConnection2 and there is already a connection created by a different application then it will share this connection and if you call WNetGetUser you will get the username used when the other application created the new connection was created.
If you call WNetCancelConnection2 on a connection that is shared between two different applications then it disconnects not just the connection for the application calling the function but it will also disconnect the other application (I have seen this with SyncBack disconnecting my test code). When you reconnect (using WNetAddConnection2 with NULL arguments) the username returned by WNetGetUser is still the username that was used by the other application when it created the connection, so it appears that username is possibly cached somewhere within the Windows Networking code. My server ignores the node/domain part of the username so I currently have SyncBack set to use subtlety different, but valid, usernames to work out what is going on.
Because calling WNetCancelConnection2 disconnects all applications it would appear to some you want to avoid, even if you know that you created a connection you cannot know if another application has started to use it. It is possible that this is the cause of Windows Explorer showing mapped drives as disconnected and other issues that I have being seeing. Also the connection only appears to be within Windows, it does not necessary cause the actually cause this connection to the server to be disconnected.
I suspect that somehow some other task run by WTS at login in the same session may be causing the problem. If I configure WTS so the test code runs in session 0 the problem does not seem to occur so this does seem to be a likely cause. This is only a suspicion and I have no proof of this and this particular system hasn’t got a lot of applications installed so it is a bit mystery if this is the case.
I can supply the test code and some of the output if this help.
Andrew.