Note that there are some explanatory texts on larger screens.

plurals
  1. POHow to access the disks mapped through RDP from a service?
    primarykey
    data
    text
    <p>RDP has this fantastic ability to let export disks from remote user's workstation to the RDP server. As far as I can tell, it is not just a windows explorer trick, but all kinds of programs can use the shortcuts "X:", "Y:", "Z:" etc... This <a href="https://stackoverflow.com/questions/9304953/copy-files-from-remote-rdp-to-local-machine">stack overflow entry</a> on RDP disk copying mentions the '\tsclient' alias which points to the machine of the RDP user. Now, it is obvious that if there are 2 or more users, they will each have their own, non-conflicting tsclient destinations. </p> <p>So, my question is this: how do I get a list of and access all remote user shared resources (disks) from a service? Ideally, if, say 2 users have connected and have shared their C: drives, i'd get a list like:</p> <ul> <li>\UserJohnDoe\VolumeXyzC - John's C drive</li> <li>\UserJaneRoe\VolumeXyzC - Jane's C drive</li> </ul> <p>Help appreciated! UPDATE:</p> <p>Here's a working piece of code (<a href="https://gist.github.com/3173572" rel="nofollow noreferrer">gist snippet</a>)</p> <pre><code>// rdpjoker by Konrads #include "stdafx.h" #define SERVER "XXX.compute-1.amazonaws.com" #define CMD "cmd.exe /C dir \\tsclient\\c &gt;output.txt" int main(int argc, char **argv){ HANDLE server; PWTS_SESSION_INFOA ppSessionInfo=NULL; WTS_SESSION_INFOA pSessionInfo; DWORD pCount; DWORD pLevel=1; DWORD i=0; LPSTR ppBuffer; DWORD bytesReturned; HANDLE userToken=NULL; HANDLE pUserToken=NULL; ULONG sessionid; DWORD dwCreationFlags=0; LPVOID environment=NULL; STARTUPINFOA si; PROCESS_INFORMATION pi; char *cmdline; char *username; char *homedir;//[MAX_PATH]; char desktop[8192]; server=WTSOpenServerA(WTS_CURRENT_SERVER_NAME); if(argc&gt;2){ sessionid=atol(argv[1]); printf("[*] Impersonating session: %i\n",sessionid); if(WTSQueryUserToken(sessionid,&amp;userToken)){ //if(DuplicateTokenEx(userToken,MAXIMUM_ALLOWED,NULL,SecurityIdentification,TokenPrimary,&amp;pUserToken)){ if(CreateEnvironmentBlock(&amp;environment,pUserToken,FALSE)){ ZeroMemory( &amp;si, sizeof( STARTUPINFO ) ); //WTSQuerySessionInformationA(server,sessionid,WTSWinStationName,&amp;ppBuffer,&amp;bytesReturned); //sprintf_s(desktop,8192,"%s\\default",ppBuffer); si.lpDesktop = "winsta0\\default";; si.cb=sizeof(STARTUPINFO); //WTSFreeMemory(ppBuffer); ZeroMemory( &amp;pi,sizeof(pi)); cmdline=(char *)malloc(MAX_PATH +1); //GetUserProfileDirectoryA(userToken,homedir,&amp;bytesReturned); //WTSUserConfigTerminalServerProfilePath //WTSQuerySessionInformationA(server,sessionid,WTSUserName,&amp;ppBuffer,&amp;bytesReturned); WTSQuerySessionInformationA(server,sessionid,WTSUserName,&amp;ppBuffer,&amp;bytesReturned); username=_strdup(ppBuffer); WTSFreeMemory(ppBuffer); //WTSQueryUserConfigA(WTS_CURRENT_SERVER_NAME,username,WTSUserConfigTerminalServerProfilePath,&amp;ppBuffer,&amp;bytesReturned); homedir=(char *)malloc(MAX_PATH); sprintf_s(homedir,MAX_PATH,"C:\\Users\\%s\\",username); //homedir=_strdup(ppBuffer); //WTSFreeMemory(ppBuffer); printf("[D] homedir: %s\n",homedir); sprintf_s(cmdline,MAX_PATH,"cmd.exe /C dir %s &gt;output.txt",argv[2]); dwCreationFlags|= CREATE_UNICODE_ENVIRONMENT | NORMAL_PRIORITY_CLASS | CREATE_NEW_CONSOLE; //WTSQuerySessionInformationA(server,sessionid,WTSWinStationName,&amp;ppBuffer,&amp;bytesReturned); //printf("station: %s",ppBuffer); if(CreateProcessAsUserA(userToken, NULL, cmdline, NULL, NULL, FALSE, dwCreationFlags, environment, homedir, &amp;si, &amp;pi)){ printf("[*]CreateProcessAsUserA succeeded! pid:%i, tid:%i\n",pi.dwProcessId,pi.dwProcessId); }else{ printf("[E] CreateProcessAsUserA failed: %i\n", GetLastError()); } //}else{ //printf("[E] CreateEnvironmentBlock failed: %i\n", GetLastError()); // } }else{ printf("[E] DuplicateTokenEx failed: %i\n", GetLastError()); } } else{ printf("[E] WTSQueryUserToken failed: %i\n", GetLastError()); exit(-1); } } else{ // no arguments specified if(WTSEnumerateSessionsA(server,0,1,&amp;ppSessionInfo,&amp;pCount)){ // printf("pCount: %i,",pCount); for (i=0;i&lt;pCount;++i){ // printf("i = %i\n",i); pSessionInfo=ppSessionInfo[i]; printf("Session ID: %i; name: %s, ",pSessionInfo.SessionId,pSessionInfo.pWinStationName); if(WTSQuerySessionInformationA(server,pSessionInfo.SessionId,WTSUserName,&amp;ppBuffer,&amp;bytesReturned)){ printf("user: %s, ",ppBuffer); WTSFreeMemory(ppBuffer); }else{ printf("WTSQuerySessionInformation[WTSUserName] failed: %i\n", GetLastError()); } if(WTSQuerySessionInformationA(server,pSessionInfo.SessionId,WTSWinStationName,&amp;ppBuffer,&amp;bytesReturned)){ printf("station: %s",ppBuffer); WTSFreeMemory(ppBuffer); }else{ printf("WTSQuerySessionInformation[WTSWinStationName] failed: %i\n", GetLastError()); } printf("\n"); } WTSFreeMemory(ppSessionInfo); }else //0014fb3c { printf("EnumerateSessions failed: %i\n", GetLastError()); } } } </code></pre>
    singulars
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload