0

I have a problem passing arguments to a powershell script from a command window. This only happens on one of my windows 10 laptops. Did I miss some configuration of powershell to handle arguments correctly?

I have set my powershell execution policy to unrestricted

PS C:\Windows> get-executionpolicy Unrestricted

My test.ps1 file is

[Byte[]] $On = 0xA0,0x01,0x01,0xA2
$port = new-Object System.IO.Ports.SerialPort $args[0],9600,None,8,one
$port.Open()
$port.Write($On, 0, $On.count)
$port.Close()

In powershell (run as administrator)

PS C:\Windows> C:\Users\me\test.ps1 "COM4"

result: success

From a CMD window (run as administrator)

C:\WINDOWS\system32>powershell -File C:\Users\me\test.ps1 "COM4"

result:

Exception calling "Open" with "0" argument(s): Access to the port 'COM4' is denied."
At C:\Users\me\test.ps1:3 char:1
+ $port.Open()
`~~~~~~~~~~~~~~
   + CategoryInfo  : NotSpecified: (:) [], MethodInvocationException
   + FullyQualifiedErrorId  : UnauthorizedAccessException
.
.

If I change the $args[0] in the ps1 file replacing it with COM4 I.E.

$port = new-Object System.IO.Ports.SerialPort COM4,9600,None,8,one

and run

C:\WINDOWS\system32>powershell -File C:\Users\me\test.ps1

result: success

So somehow the argument string is not being parsed correctly. If I put in this debug code in the original ps1 file:

echo "input arg >" $args[0] "<"

then the output is:

input arg >
COM4
<

I.E. there are carriage returns on either side of the args[0] string.

Oddly - this problem only happens on one of my laptops - the other (also windows 10) handles this ps1 script with the "COM4" arguments just fine. Somehow there's a difference between the argument handling on the two machines. The debug output (above) on the laptop that runs the script properly is identical - I.E. with the carriage returns either side of the COM4 text.

6
  • The symptom is mysterious and the mystery is well worth solving, as it is very likely to continue to cause problems. As a stopgap you can apply .Trim() to your aguments: $args[0].Trim() Commented Jun 9, 2023 at 12:53
  • What is interesting is the command works with no quotes and doesn't work with quotes. try removing the quotes. Commented Jun 9, 2023 at 12:54
  • @jdweng - whether you pass "COM4" or COM4 as an argument makes no difference - the script (normally) sees verbatim, unquoted COM4. The issue isn't one of quoting (note that the diagnostic output has no quotes), but one of extraneous surrounding newlines. Conceivably, there could be hidden control characters in the argument string (though I wouldn't know which specific ones would cause this symptom). Commented Jun 9, 2023 at 13:01
  • @mklement0 : As I said earlier in the week I do not trust the documentation. There are lots of inconsistencies and lets find out what the OP says. I prefer Unix over DOS/Windows. Commented Jun 9, 2023 at 13:27
  • @jdweng, I didn't mention any documentation, and your preference of OS is also not relevant to this question. Nothing in the question suggests that quoting is a factor. Commented Jun 9, 2023 at 16:00

2 Answers 2

0

Consider defining an input parameter to represent your first argument. Add something like this to the top for your script file:

Param (
    [Parameter(Position=0)][String] $name
)

Then use $name to represent your argument in your script.

This is the standard for inject parameters to a Powershell script. Additionally, there is much more to parameters than my example here, so check out this documentation, if you are interested. Your usage of the script from CMD looks file, too.

Sign up to request clarification or add additional context in comments.

1 Comment

While it's definitely preferable in general to declare parameters, accepting positional arguments such as "COM4" definitely normally also works via the automatic $args array, with$args[0] referring to the first positional argument. Therefore, your recommendation cannot be expected to make a difference. The cause of the OP's symptom is unknown at this point, and the fact that it happens on just one machine suggests that the problem is unusual.
0

This is a work-around.

The test.ps1 file now reads : The sleep command has been added

[Byte[]] $On = 0xA0,0x01,0x01,0xA2
Start-Sleep -Seconds 2
$port = new-Object System.IO.Ports.SerialPort $args[0],9600,None,8,one
$port.Open()
$port.Write($On, 0, $On.count)
$port.Close()

I can now call:

C:\WINDOWS\system32>powershell -File C:\Users\me\test.ps1 "COM4"

result : success

and I can call the same line from a bat file and that works too.

Setting the sleep time to less than 2 seconds results in the failure message.

It appears to be a timing issue. I first tried the Trim idea with no luck, then put Write-Verbose and Set-PSDebug -Trace 1 because sometimes writing loads of stuff to the console helps with debugging. No luck there.
The 2 second delay before the $port = new-Object line 'solves' the problem. Then the Open() command only fails 10% of the time (roughly). Because it still fails occasionally, I call the new-Object / open() block a couple of times with a 2 second delay between. Makes for slower code but at least the work-around works consistently. I tried a 1 second delay and that didn't work.

So there must be some issue with the bat file calling the PS script and the PS script not having all the command line info when it compiles the code before running. Does powershell parse each line and then execute it or does it compile the whole script before running it?

Since I can print out the value of the $args[0], clearly by the time powershell processes the echo command, the $args[0] is present, ready to be printed out. This echo part is consistent.

The machine is a fairly OK Toshiba laptop with a clean install of W10. Otherwise functions fine. The COM port is instructing the built-in bluetooth interface, sending commands to a external bluetooth relay.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.