powershell script to test if a USB is attached

Hi,

I have a shell script that works using Windows Subsystem for Linux (WSL) which does the following:

  1. determines if we have a USB device
  2. if not, and is used by someone else, disconnect the USB device
  3. connect the USB device

I now have a requirement to convert this to a powershell script where by it does the same thing and returns either success (we have the device) or fail (we don't have the device).

My current shell script follows.  Any help, pointers, in using powershell and the VirtualHere Client API would be much appreciated.

Thanks in-advance

Clive

 

#Check if the USB is ours
vhui64.exe -t "LIST" -r "c:/Apps/tmp/vh-usb-list.txt"


# Possible states
# Token JC (meteor.13) - available
# Token JC (meteor.13) (In-use by you) - we have it
# Token JC (meteor.13) (In-use by:SYSTEM (SYSTEM) at 192.168.102.4) - someone else has it
#
USBMINE=`grep -i "Token JC (meteor.13) (In-use by you)" /mnt/c/Apps/tmp/vh-usb-list.txt`
if [ -z "${USBMINE}" ]
then
    USBMINE=`grep -i "Token JC (meteor.13) (In-use by" /mnt/c/Apps/tmp/vh-usb-list.txt`
    if [ -n "${USBMINE}" ]
    then
        echo ${USBMINE}
        echo -n "STOP USING,meteor.13 - "
        vhui64.exe -t "STOP USING,meteor.13"        
        sleep 2

        # recheck
        vhui64.exe -t "LIST" -r "c:/Apps/tmp/vh-usb-list.txt"
        USBMINE=`grep -i "Token JC (meteor.13) (In-use by" /mnt/c/Apps/tmp/vh-usb-list.txt`
        if [ -z "${USBMINE}" ]
        then
            # successfully unmounted
            LOAD=yes
        fi
    else
        # unmounted
        LOAD=yes
    fi
else
    # we already have it mounted
    LOAD=no
fi


# Mount the USB
if [ "${LOAD}" = yes ]
then
    echo -n "USE,meteor.13 - "
    vhui64.exe -t "USE,meteor.13"        
    sleep 1
fi

 

#2

Sorry i dont know much powershell so i cant help.

#3

Hi,

I found this under the Client API post.  Would anyone know how to convert the 'LIST' section into function that can reused?

Thanks

$pipeClient = new-object System.IO.Pipes.NamedPipeClientStream("vhclient")
$pipeClient.Connect()
$pipeClient.ReadMode = [System.IO.Pipes.PipeTransmissionMode]::Message
$writer = new-object System.IO.StreamWriter($pipeClient)
$writer.AutoFlush = $true
$writer.Write("LIST")
$reader = new-object System.IO.StreamReader($pipeClient)
$bytes = New-Object System.Collections.Generic.List[byte]
while ($reader.Peek() -ne -1)
{
  $bytes.Add($reader.Read())
}
$result = [System.Text.Encoding]::UTF8.GetString($bytes)

#4

This is what I eventually got to work.

# Possible scenarios
# Token JC (myusbdrive.XX) - USB token available
# Token JC (myusbdrive.XX) (In-use by you) - it's currently mine
# Token JC (myusbdrive.XX) (In-use by:SYSTEM (SYSTEM) at 192.168.0.34) - someone else has it
#

# Report USB drive's attached
#
function eToken_List () {
    $pipeClient = new-object System.IO.Pipes.NamedPipeClientStream("vhclient")
    $pipeClient.Connect()
    $pipeClient.ReadMode = [System.IO.Pipes.PipeTransmissionMode]::Message

    $writer = new-object System.IO.StreamWriter($pipeClient)
    $writer.AutoFlush = $true

    $reader = new-object System.IO.StreamReader($pipeClient)

    $bytes = New-Object System.Collections.Generic.List[byte]

    $writer.Write("LIST")

    while ($reader.Peek() -ne -1)
    {
      $bytes.Add($reader.Read())

    }

    $pipeClient.Dispose()

    $result = [System.Text.Encoding]::UTF8.GetString($bytes)
    $result
    return
}

# Disconnect a USB drive
#
function eToken_Stop ( $token ) {
    $pipeClient = new-object System.IO.Pipes.NamedPipeClientStream("vhclient")
    $pipeClient.Connect()
    
    $writer = new-object System.IO.StreamWriter($pipeClient)
    $writer.AutoFlush = $true

    $token = 'STOP USING,' + $token
    Write-Host $token
    $writer.Write($token)
    Start-Sleep -m 1000

    $pipeClient.Dispose()
}

# Connect a USB drive
#
function eToken_Use ( $token ) {
    $pipeClient = new-object System.IO.Pipes.NamedPipeClientStream("vhclient")
    $pipeClient.Connect()
    
    $writer = new-object System.IO.StreamWriter($pipeClient)
    $writer.AutoFlush = $true

    $token = 'USE,' + $token
    Write-Host $token
    $writer.Write($token)
    Start-Sleep -m 1000

    $pipeClient.Dispose()
}

 

# token details we want to mount

$etoken = 'myusbdrive.XX'
$mount = 'failed'


# file to stash the VirtualHere info
# NB: Couldn't get the result to pipe even with Out-String -Stream | Select-String!

$filename = Get-Random
$filename = 'C:\' + $filename + '.txt'


eToken_List | Out-File -FilePath $filename -Encoding ASCII
$mytoken = Select-String -Pattern ('Token JC \(' + $etoken + '\) \(In-use by you') -Path $filename -Quiet
if ($mytoken -eq $false ) {

    # Is the token being used by someone else?

    $mytoken = Select-String -Pattern ('Token JC \(' + $etoken + '\) \(In-use by') -Path $filename -Quiet
    if ($mytoken -eq $true ) {
        eToken_Stop $etoken

        # recheck that token is now free

        eToken_List | Out-File -FilePath $filename -Encoding ASCII
        $mytoken = Select-String -Pattern ('Token JC \(' + $etoken + '\) \(In-use by') -Path $filename -Quiet
        if ($mytoken -eq $false ) {
            $mount = 'yes'
        }
    }
    else {
    
        # No one has the token
        
        $mount = 'yes'
    }
}
else {
    
    # We already have the token
    
    $mount = 'no'
}


# Housekeeping

Remove-Item $filename

 

# mount our token and exit

if ( $mount -eq 'yes' ) {
    eToken_Use $etoken
    exit 0
}
else {
    if ( $mount = 'no' ) {
        exit 0
    }
    else {
        exit 1
    }
}

#5

Thanks for that, it might be helpful for others