How to Find current user in shellcommand? - shell

When running command prompt in Standard user account echo %userprofile% command shows current user name but when run as administrator it will shows admin user name.
How can i get current standard user name even the command prompt in run as administrator mode? What ShellCommand is used for this?

I found the solution.
for /f "tokens=2" %u in ('query session ^| findstr /R "^>"') do #echo %u
It works.

Related

Batch script access denied even with admin privileges

I have a batch script in Windows7 to update the hosts file that fails.
I am logged as a user with administrative rights.
Even if I run the script with the "Run as administrator" option I get Access denied. 0 files copied when executing this part of the script:
for /f "tokens=1-2 delims=:" %%a in ('ipconfig^|find "IPv4"') do set ip=%%b
set ip=%ip:~1%
REM create changing part of hosts file...
if exist %temp%\temp.txt del %temp%\temp.txt
echo %ip% myproxy >> %temp%\temp.txt
REM check this...
set hostpath=C:\WINDOWS\system32\drivers\etc
REM add static part of hosts file
type "%hostpath%\hosts-static" >> %temp%\temp.txt
REM replace hosts file
copy /y %temp%\temp.txt "%hostpath%\hosts"
ipconfig /flushdns
netsh interface IP delete arpcache
pause
I also tried to create a shortcut and set the "Advanced -> Run as Administrator" option but no luck.
If I open a cmd shell as Administrator and then run the script from there everything works fine, but no way of running it directly double-clicking on the file (or its link).
Any idea?
EDIT:
added the whole script.
I tried creating a shortcut for the following command to execute as Administrator
C:\Windows\System32\cmd.exe /c script.bat
and it is also failing.
From the same shortcut (without arguments) I can open a window where I can execute the batch correctly. I really cannot see why.
Obviously a late response, but just solved this issue with a very straightforward solution so I thought I'd share:
Using ICACLS you can modify access control lists (ACLs) to bypass access denied errors.
Run the following command:
ICACLS C:\path\to\batch\file\directory\* /C
the parameter /C tells the batch file to bypass access denied errors. Cheers.
Try attrib -r -s -h -a "%hostpath%\hosts" before your copy command. If any file is attributed +r, +s, or +h, you'll get "Access is denied" if you try to overwrite it using copy.

batch file will not run as administrator

I am trying to run this code in a windows batch (.bat) file
#echo off
echo Adding New User - LogMeInRemoteUser
net user | find /i "LogMeInRemoteUser" || Net user LogMeInRemoteUser password /add /fullname:"LogMeInRemoteUser"
pause
echo Adding User to Administrators Group
NET LOCALGROUP Administrators "LogMeInRemoteUser" /ADD
pause
echo Creating Registry Keys to remove the new user from the login page
REG ADD "HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\WinLogon\SpecialAccounts\UserList" /v "LogMeInRemoteUser" /t REG_DWORD /d 0
pause
echo Finished
if i run the file normally, i get an Access Denied error so I try to run as Administrator but the cmd windows opens and instantly closes, what have i done wrong?
When you run as administrator the current directory is changed under you. To prove that (and fix it) enter these 3 lines under your #echo off
echo(%cd%
pushd %~dp0
echo(%cd%
You can remove both of the echo( statements after you see what is happening.

Reset rdp session with psexec

We have domain users that use a remote instance of an app through RDP. The app is quite buggy, and their session needs reset frequently. I'd like to build a script that uses psexec from the client to reset the session on the server.
psexec \\server -u user -p pass query session
shows all the sessions
psexec \\server -u user -p pass reset session_id
resets the session based upon the id.
I need a way to reset the session based upon the username, instead of session name or id
Try this combination of commands to get the username and then you can kill the session by id. You will need PsLoggedOn from Windows Sysinternals Here is the a link which explains the commands. How to check who has logged into your system
PSLOGGEDON -L \\remotecomputeror
PSEXEC \\remotecomputer NET CONFIG WORKSTATION | FIND /I " name "
PSEXEC \\remotecomputer NET NAME
PSEXEC \\remotecomputer NETSH DIAG SHOW COMPUTER /V | FIND /i "username"
FOR /F %%A IN ('REG Query \\remotecomputer\HKU ˆ| FINDSTR /R /B /C:"HKEY_USERS\\S-1-5-[0-9][0-9]-[0-9-]*$"') DO (
FOR /F "tokens=3 delims=\" %%B IN ('REG Query "\\remotecomputer\%%A\Volatile Environment"') DO (
SET LoggedinUser=%%B
)
)

How to detect if CMD is running as Administrator/has elevated privileges?

From inside a batch file, I would like to test whether I'm running with Administrator/elevated privileges.
The username doesn't change when "Run as Administrator" is selected, so that doesn't work.
If there were a universally available command, which has no effect, but requires administrative privileges, then I could run that and check for an error code in order to test for privileges. So far, I haven't found such a command. The commands I have found seem to return a single, non-specific error code, which could indicate anything, and they're prone to failure for a variety of reasons.
I only care about Windows 7, though support of earlier operating systems would be nice.
This trick only requires one command: type net session into the command prompt.
If you are NOT an admin, you get an access is denied message.
System error 5 has occurred.
Access is denied.
If you ARE an admin, you get a different message, the most common being:
There are no entries in the list.
From MS Technet:
Used without parameters, net session displays information about all
sessions with the local computer.
ADDENDUM: For Windows 8 this will not work; see this excellent answer instead.
Found this solution here: http://www.robvanderwoude.com/clevertricks.php
AT > NUL
IF %ERRORLEVEL% EQU 0 (
ECHO you are Administrator
) ELSE (
ECHO you are NOT Administrator. Exiting...
PING 127.0.0.1 > NUL 2>&1
EXIT /B 1
)
Assuming that doesn't work and since we're talking Win7 you could use the following in Powershell if that's suitable:
$principal = new-object System.Security.Principal.WindowsPrincipal([System.Security.Principal.WindowsIdentity]::GetCurrent())
$principal.IsInRole([System.Security.Principal.WindowsBuiltInRole]::Administrator)
If not (and probably not, since you explicitly proposed batch files) then you could write the above in .NET and return an exit code from an exe based on the result for your batch file to use.
I like Rushyo's suggestion of using AT, but this is another option:
whoami /groups | findstr /b BUILTIN\Administrators | findstr /c:"Enabled group" && goto :isadministrator
This approach would also allow you to distinguish between a non-administrator and a non-elevated administrator if you wanted to. Non-elevated administrators still have BUILTIN\Administrators in the group list but it is not enabled.
However, this will not work on some non-English language systems. Instead, try
whoami /groups | findstr /c:" S-1-5-32-544 " | findstr /c:" Enabled group" && goto :isadministrator
(This should work on Windows 7 but I'm not sure about earlier versions.)
Pretty much what others have put before, but as a one liner that can be put at the beginning of a batch command. (Well, usually after #echo off.)
net.exe session 1>NUL 2>NUL || (Echo This script requires elevated rights. & Exit /b 1)
The easiest way to do this on Vista, Win 7 and above is enumerating token groups and looking for the current integrity level (or the administrators sid, if only group memberhip is important):
Check if we are running elevated:
whoami /groups | find "S-1-16-12288" && Echo I am running elevated, so I must be an admin anyway ;-)
Check if we belong to local administrators:
whoami /groups | find "S-1-5-32-544" && Echo I am a local admin
Check if we belong to domain admins:
whoami /groups | find "-512 " && Echo I am a domain admin
The following article lists the integrity level SIDs windows uses: http://msdn.microsoft.com/en-us/library/bb625963.aspx
Here's a slight modification of Harry's answer that focuses on elevated status; I'm using this at the start of an install.bat file:
set IS_ELEVATED=0
whoami /groups | findstr /b /c:"Mandatory Label\High Mandatory Level" | findstr /c:"Enabled group" > nul: && set IS_ELEVATED=1
if %IS_ELEVATED%==0 (
echo You must run the command prompt as administrator to install.
exit /b 1
)
This definitely worked for me and the principle seems to be sound; from MSFT's Chris Jackson:
When you are running elevated, your token contains an ACE called Mandatory Label\High Mandatory Level.
the solution:
at >nul
if %ErrorLevel% equ 0 ( echo Administrator ) else ( echo NOT Administrator )
does not work under Windows 10
for all versions of Windows can be do so:
openfiles >nul 2>&1
if %ErrorLevel% equ 0 ( echo Administrator ) else ( echo NOT Administrator )
I read many (most?) of the responses, then developed a bat file that works for me in Win 8.1. Thought I'd share it.
setlocal
set runState=user
whoami /groups | findstr /b /c:"Mandatory Label\High Mandatory Level" > nul && set runState=admin
whoami /groups | findstr /b /c:"Mandatory Label\System Mandatory Level" > nul && set runState=system
echo Running in state: "%runState%"
if not "%runState%"=="user" goto notUser
echo Do user stuff...
goto end
:notUser
if not "%runState%"=="admin" goto notAdmin
echo Do admin stuff...
goto end
:notAdmin
if not "%runState%"=="system" goto notSystem
echo Do admin stuff...
goto end
:notSystem
echo Do common stuff...
:end
Hope someone finds this useful :)
A "not-a-one-liner" version of https://stackoverflow.com/a/38856823/2193477
#echo off
net.exe session 1>NUL 2>NUL || goto :not_admin
echo SUCCESS
goto :eof
:not_admin
echo ERROR: Please run as a local administrator.
exit /b 1
I know I'm really late to this party, but here's my one liner to determine admin-hood.
It doesn't rely on error level, just on systeminfo:
for /f "tokens=1-6" %%a in ('"net user "%username%" | find /i "Local Group Memberships""') do (set admin=yes & if not "%%d" == "*Administrators" (set admin=no) & echo %admin%)
It returns either yes or no, depending on the user's admin status...
It also sets the value of the variable "admin" to equal yes or no accordingly.
Here's a simple method I've used on Windows 7 through Windows 10. Basically, I simply use the "IF EXIST" command to check for the Windows\System32\WDI\LogFiles folder. The WDI folder exists on every install of Windows from at least 7 onward, and it requires admin privileges to access. The WDI folder always has a LogFiles folder inside it. So, running "IF EXIST" on the WDI\LogFiles folder will return true if run as admin, and false if not run as admin. This can be used in a batch file to check privilege level, and branch to whichever commands you desire based on that result.
Here's a brief snippet of example code:
IF EXIST %SYSTEMROOT%\SYSTEM32\WDI\LOGFILES GOTO GOTADMIN
(Commands for running with normal privileges)
:GOTADMIN
(Commands for running with admin privileges)
Keep in mind that this method assumes the default security permissions have not been modified on the WDI folder (which is unlikely to happen in most situations, but please see caveat #2 below). Even in that case, it's simply a matter of modifying the code to check for a different common file/folder that requires admin access (System32\config\SAM may be a good alternate candidate), or you could even create your own specifically for that purpose.
There are two caveats about this method though:
Disabling UAC will likely break it through the simple fact that everything would be run as admin anyway.
Attempting to open the WDI folder in Windows Explorer and then clicking "Continue" when prompted will add permanent access rights for that user account, thus breaking my method. If this happens, it can be fixed by removing the user account from the WDI folder security permissions. If for any reason the user MUST be able to access the WDI folder with Windows Explorer, then you'd have to modify the code to check a different folder (as mentioned above, creating your own specifically for this purpose may be a good choice).
So, admittedly my method isn't perfect since it can be broken, but it's a relatively quick method that's easy to implement, is equally compatible with all versions of Windows 7, 8 and 10, and provided I stay mindful of the mentioned caveats has been 100% effective for me.
Works for Win7 Enterprise and Win10 Enterprise
#if DEFINED SESSIONNAME (
#echo.
#echo You must right click to "Run as administrator"
#echo Try again
#echo.
#pause
#goto :EOF
)
If you are running as a user with administrator rights then environment variable SessionName will NOT be defined and you still don't have administrator rights when running a batch file.
You should use "net session" command and look for an error return code of "0" to verify administrator rights.
Example;
- the first echo statement is the bell character
net session >nul 2>&1
if not %errorlevel%==0 (echo
echo You need to start over and right-click on this file,
echo then select "Run as administrator" to be successfull.
echo.&pause&exit)
Unfortunately, "S-1-5-32-544" that others have suggested is not proof of elevation.
Windows 10 and higher, a language independent approach is:
whoami /groups | find "S-1-16-12288"
this is the "High Mandatory Level", which is actually escalated.
Regular command prompt:
C:\> whoami /groups | find "S-1-16-12288"
C:\>
Administrator command prompt:
C:\> whoami /groups | find "S-1-16-12288"
Mandatory Label\High Mandatory Level Label S-1-16-12288
C:\>
To use in a .bat file:
whoami /groups | find "S-1-16-12288" && set ELEVATED=true || set ELEVATED=false
You can also use this from powershell:
function is_elevated() {
Param( [String] $ToGroup = "S-1-16-12288" )
return [bool] ( whoami /groups | select-string $ToGroup )
}
for example:
PS> cd c:/temp
PS> set-content is-elevated.ps1 "return [bool] ( whoami /groups | sls S-1-16-12288 )"
PS> ./is-elevated.ps1
False
PS> start -verb runas powershell.exe
...
PS C:\Windows\system32> cd \temp
PS C:\temp> ./is-elevated.ps1
True
Thanks Torin Darkflight,
Your method is the only one that work for me on Windows 11.
Here's an example script expanding on your post:
IF EXIST %SYSTEMROOT%\SYSTEM32\WDI\LOGFILES GOTO :Running_As_An_Admin
ECHO You are NOT an Administrator. This command requires admin rights. & Echo: & Echo Quitting......
#TIMEOUT /T 10
goto :QUIT
:Running_As_An_Admin
Echo Do Admin stuff here!!!
:QUIT

How do you find the current user in a Windows environment?

When running a command-line script, is it possible to get the name of the current user?
You can use the username variable: %USERNAME%
Username:
echo %USERNAME%
Domainname:
echo %USERDOMAIN%
You can get a complete list of environment variables by running the command set from the command prompt.
Just use this command in command prompt
C:\> whoami
It should be in %USERNAME%. Obviously this can be easily spoofed, so don't rely on it for security.
Useful tip: type set in a command prompt will list all environment variables.
%USERNAME% is the correct answer in batch and other in Windows environments.
Another option is to use %USERPROFILE% to get the user's path, like C:\Users\username.
The answer depends on which "command-line script" language you are in.
Cmd
In the old cmd.exe command prompt or in a .bat or .cmd script, you can use the following:
%USERNAME% - Gets just the username.
%USERDOMAIN% - Gets the user's domain.
PowerShell
In the PowerShell command prompt or a .ps1 or .psm1 script, you can use the following:
[System.Security.Principal.WindowsIdentity]::GetCurrent().Name - Gives you the fully qualified username (e.g. Domain\Username). This is also the most secure method because it cannot be overridden by the user like the other $Env variables below.
$Env:Username - Gets just the username.
$Env:UserDomain - Gets the user's domain.
$Env:ComputerName - Gets the name of the computer.
Any Shell
whoami - Gets the user's domain and username in the format "domain\username".
This also works on Unix systems as well, not just Windows, so it's a nice cross-platform solution.
%USERNAME% will get you the username of the currently running process. Depending on how you are running your batch file, this is not necessarily the same as the name of the current user. For example, you might be running your batch file through a scheduled task, from a service, etc.
Here is a more sure way of getting the username of the currently logged on user by scraping the name of the user that started the explorer.exe task:
for /f "TOKENS=1,2,*" %%a in ('tasklist /FI "IMAGENAME eq explorer.exe" /FO LIST /V') do if /i "%%a %%b"=="User Name:" set _currdomain_user=%%c
for /f "TOKENS=1,2 DELIMS=\" %%a in ("%_currdomain_user%") do set _currdomain=%%a & set _curruser=%%b
I use this method in writing batch files for testing.
echo %userdomain%\%username%
Since you must include the password in plain text if authentication is required, I will only use it in a completely private environment where other users cannot view it or if a user seeing the password would bear no consequences.
Hope this helps someone out.
In most cases, the %USERNAME% variable will be what you want.
echo %USERNAME%
However, if you're running an elevated cmd shell, then %USERNAME% will report the administrator name instead of your own user name. If you want to know the latter, run:
for /f "tokens=2" %u in ('query session ^| findstr /R "^>"') do #echo %u
It's always annoyed me how Windows doesn't have some of more useful little scripting utilities of Unix, such as who/whoami, sed and AWK. Anyway, if you want something foolproof, get Visual Studio Express and compile the following:
#include <windows.h>
#include <stdio.h>
int main(int argc, char **argv) {
printf("%s", GetUserName());
}
And just use that in your batch file.
Just type whoami in command prompt and you'll get the current username.
This is the main difference between username variable and whoami command:
C:\Users\user.name>echo %username%
user.name
C:\Users\user.name>whoami
domain\user.name
DOMAIN = bios name of the domain (not fqdn)
Via powershell (file.ps1)
I use the following
$username = [System.Security.Principal.WindowsIdentity]::GetCurrent().Name
It returns the name of the user in the "Domain\Username" format.
If you just want the username just write
$username = [System.Security.Principal.WindowsIdentity]::GetCurrent().Name.Split("\")[1]
The advantage is that It works with windows 10 windows 8 server 2016. As far as I remember with also other OS like Win7 etc. (not older)
. And yeah via batch you can simply use
$username = &whoami
In a standard context, each connected user holds an explorer.exe process: The command [tasklist /V|find "explorer"] returns a line that contains the explorer.exe process owner's, with an adapted regex it is possible to obtain the required value. This also runs perfectly under Windows 7.
In rare cases explorer.exe is replaced by another program, the find filter can be adapted to match this case. If the command return an empty line then it is likely that no user is logged on. With Windows 7 it is also possible to run [query session|find ">"].
As far as find BlueBearr response the best (while I,m running my batch script with eg. SYSTEM rights) I have to add something to it.
Because in my Windows language version (Polish) line that is to be catched by "%%a %%b"=="User Name:" gets REALLY COMPLICATED (it contains some diacritic characters in my language) I skip first 7 lines and operate on the 8th.
#for /f "SKIP= 7 TOKENS=3,4 DELIMS=\ " %%G in ('tasklist /FI "IMAGENAME eq explorer.exe" /FO LIST /V') do #IF %%G==%COMPUTERNAME% set _currdomain_user=%%H

Resources