Passing variable to PowerShell - windows

I'm trying to pass a variable to this command in PowerShell
Start-Process $devconloc -ArgumentList "\disable" '"'$GPUList[1]'"' -ErrorAction Stop
$GPUList[0] is a hardware ID and needs to be passed to devcon.exe in quotes:
"PCI\VEN_10DE&DEV_1CBB&SUBSYS_087D1028&REV_A1\4&44A1B07&0&0008"
But I get the following error
Start-Process : A positional parameter cannot be found that accepts argument '"'.
Any ideas what is happening?

Like the others allready pointed out in the comments, there are two problems here:
You should pass a string-array to -ArgumentList. You do this by seperating you arguments with a ,. Not a whitespace.
To fill in the object $GPUList[1] correct with your " around the string, there are two ways to fill the string with object:
Escaping the " in the string with ` and phrasing the variables in () to make sure the array position will be taken in notice : -ArgumentList '\disable', `"$($GPUList[1])`"
Filling in the variable with a position reference: -ArgumentList 'disable', ('"{0}"' -f $GPUList[1])

Related

Running a command on all files in PowerShell command prompt [duplicate]

In GNU/Linux I would do:
PROGPATH=/long/and/complicated/path/to/some/bin
$PROGPATH/program args...
but in Powershell if I try this:
$PROGPATH=\long\and\complicated\path\to\some\bin
$PROGPATH\program args...
I get:
At script.ps1:2 char:...
+ $PROGPATH\program args ...
+ ~~~~~~~~
Unexpected token '\program' in expression or statement.
+ CategoryInfo : ParserError: (:) [], ParseException
+ FullyQualifiedErrorId : UnexpectedToken
So how do I do this simple thing I know how to do in bash, in Powershell?
js2010's helpful answer shows the correct solution:
Because your command name/path contains a variable reference ($PROGPATH/...), you must invoke it with &.
The same applies if a grouping expression, (...) is used, or a subexpression, $(...) is involved.
Additionally, the same applies if a command name/path is quoted ('...' or "...")[1], as is required if the path contains spaces, for instance.
To put it differently: Direct invocation is only supported if the command name/path is a verbatim, unquoted string[1]; in all other cases, & must be used.
As for why:
&, the call operator is necessary to force interpretation of a statement as a command, i.e. to have it parsed in argument mode (see below), so as to result in command execution rather than expression evaluation.
PowerShell has two fundamental parsing modes:
argument mode, which works like a traditional shell, where the first token is a command name/path, such as a cmdlet or an external program, with subsequent tokens representing the arguments, which only require quoting if they contain shell metacharacters (chars. with special meaning to PowerShell, such as spaces to separate tokens).
expression mode, which works like expressions in programming languages.
PowerShell decides based on a statement's first token what parsing mode to apply:
If, among other things, the first token starts with a variable reference or is a quoted string, PowerShell parses in expression mode.
In expression mode, \ starts a new token, and unrecognized token \program results in the syntax error you saw.
(If you had used /, it would have been interpreted as the division operator, and program wouldn't be a valid divisor operand.)
[1] Note that if your executable path is a literal string (doesn't contain variable references of expressions) you may alternatively `-escape individual characters (spaces) in lieu of enclosing entire string in '...' or "...", in which case & is then not necessary; e.g.:
C:\Program` Files\Notepad++\notepad++.exe
With a literal string you can even employ partial single- or double-quoting as long as the first token is unquoted; e.g.:
C:\"Program Files"\Notepad++\notepad++.exe
Use the call operator "&". https://ss64.com/ps/call.html
Related: Executing a command stored in a variable from PowerShell
$progpath = 'c:\windows\system32'
& $progpath\notepad somefile.txt
Something with a space:
& 'C:\Program Files\internet explorer\iexplore' yahoo.com
Other options, adding to the path:
$env:path += ';C:\Program Files\internet explorer'
iexplore yahoo.com
And backquoting the spaces:
C:\Program` Files\internet` explorer\iexplore yahoo.com

Repeating character for divider line in PowerShell

This is just a question of curiosity to better learn how PowerShell works. Why can I put the repeating string into a variable, but not put it in a Write-Host statement? The purpose is to print a row of dashes as a divider.
$divider = "-"*25
Write-Host $divider
Write-Host "-"*25
Write-Host $("-"*25) #is this the best way to do it with a var?
Results Window:
-------------------------
- *25
-------------------------
In, Write-Host "-"*25, it is evaluated as an argument to the function instead of an expression. So, parenthesis need to be used to get it as an expression first and then result of this expression passed as an argument to Write-Host.
Check the about Parsing

How set preference `$ErrorView = "CategoryView"` before start powershell.exe

How to set preference $ErrorView = "CategoryView" before start powershell.exe ?
powershell.exe -command "$ErrorView = "CategoryView" ; dir wrong.txt" doesnt work.
your code has a serious error in it. you used 4 double quotes instead of two on the outside and a pair of single quotes on the inside. [grin]
this works ...
powershell.exe -command "$ErrorView = 'CategoryView' ; dir wrong.txt; pause"
remove the pause when you are certain things are working as needed. [grin]
To complement Lee Dailey's helpful answer: As Lee points out, your primary problem is that you neglected to escape the " chars. embedded in your overall "..." command.
Assuming that you're calling your command from outside of PowerShell, such as from cmd.exe (Command Prompt):
Using embedded single-quoting ('...') in lieu of the embedded "..." is an option in this case, as shown in Lee's answer, because CategoryView is to be treated as a literal string.
Using ' for the embedded quoting conveniently obviates the need for escaping.
However, in cases where the embedded string contains variable references (e.g., $var) or expressions (e.g, $(Get-Date)), use of a double-quoted string ("...") is a must, because only double-quoted strings are expandable (interpolated). Escaping the embedded " as \" is then a must.
Note that, by contrast, inside PowerShell " chars. must be escaped as `".
# From cmd.exe, for instance.
C:\>powershell.exe -command "$ErrorView = \"CategoryView\"; dir wrong.txt"
If, for some reason, you must invoke another PowerShell instance from within PowerShell, use a script block ({ ... }), which also obviates the need for escaping (and better integrates with the calling session by returning objects from the invocation, not just strings).
# From Powershell.
PS> powershell.exe -command { $ErrorView = "CategoryView" ; dir wrong.txt }

How to find substring returned from PowerShell function with command SET in batch file?

I've called .ps1 function in batch file and assigned the result to $Value variable:
for /f "delims=" %%a in ('powershell -ExecutionPolicy Bypass .\test.ps1 -TargetGroupArn "arn:aws:elasticloadbalancing:eu-west-1:570226278193:targetgroup/whocms-uat/cc28ab2765d2503c" -TargetId "i-01fab6896b4efa925" -state "healthy" -timeout 240') do Set "$Value=%%a"
When checked with echo it prints the correct result: 09/13/2018 16:34:34 : healthy
Echo Value received from PowerShell : %$Value%
But I am not able to check if the result contains substring:
set str1=%Value%
if not x%str1:healthy=%==x%str1% echo It contains healthy
The solution is quite simple:
if not "%$Value:healthy=%" == "%$Value%" echo It contains healthy
The double quotes around the two string arguments between the operator == results in interpreting everything between " as literal characters by IF. Otherwise a space inside value string is interpreted as argument separator.
IF includes the double quotes on comparing the two strings. This means on using "..." for one argument, "..." must be also used on other argument as otherwise the two compared strings are never equal.
For even more details on how IF compares strings or integers see the answer on Symbol equivalent to NEQ, LSS, GTR, etc. in Windows batch files.
PS: $ has no special meaning for Windows command processor on being used in an environment variable name. It is interpreted as literal character like a letter.

Replacing strings in a PowerShell file and then calling it via batch + command line arguments

This is my PowerShell file:
#Replace.ps1
Param(
[string]$filepath,
[string]$find,
[string]$replace
)
$content = Get-Content $filepath
$content = $content.replace($find,$replace)
$content | out-file $filepath
This is the batch file which I am using it to call this
#ChangeIP.bat
#echo on
powershell.exe -File E:\Replace.ps1 %1 %2 %3
Now when I try to call the batch file from cmd as:
ChangeIP.bat "E:\foreign logs.txt" firstword secondword
then it is showing some ridiculous errors.
I basically am stuck in passing the file name (which is having white spaces).
The code I need basically should be able to do the following things:
A PowerShell script that takes three command line arguments:
FilePath // With white spaces (don't know how)
String to replace
String to be replaced with
The PowerShell script should be able to fetch the contents of the "FilePath" supplied. Find the "String to replace" string and Replace it with "String to be replaced with" string
Then calling this PowerShell script via batch file and supplying the three command line arguments there.
Please keep in the mind, the file path contains spaces.
Try the -replace operator instead of the Replace() method in case you're starting PowerShell v2:
$content = $content -replace $find $replace

Resources