Search code examples
for-loopbatch-filecmdbcdedit

Remove trailing spaces from the output Batch Script


The results of CMD command:

bcdedit /enum firmware | findstr "description"

is:

description             ATA HDD: ADATA SU650                             
description             LinuxMint
description             DisablePROCHOT UEFI
description             rEFInd Boot Manager

I make the Batch script below and run it:

@echo off
setlocal EnableDelayedExpansion
set "fwdes=bcdedit /enum firmware ^| findstr "description""
for /f "usebackq Tokens=1*" %%a in (`%fwdes%`) do echo [%%b]
pause

The output is:

[ATA HDD: ADATA SU650                             ]
[LinuxMint]
[DisablePROCHOT UEFI]
[rEFInd Boot Manager]

From the output, there are lots of extra spaces after SU650

How could I remove them to become just [ATA HDD: ADATA SU650] like on the other lines?


Update

After tried several times, i found the way:

@echo off
setlocal EnableDelayedExpansion
set Sys32=%SystemRoot%\System32
set "fwdes=%Sys32%\bcdedit.exe /enum firmware^| %Sys32%\findstr.exe "description""
for /f "usebackq Tokens=1*" %%a in (`%fwdes%`) do (
    echo %%b | %Sys32%\findstr.exe /c:"SU650" >nul && (
    for /f "Tokens=1-4" %%s in ('echo %%b') do echo [%%s %%t %%u %%v]) || (echo [%%b])
)
pause

The output is:

[ATA HDD: ADATA SU650]
[LinuxMint]
[DisablePROCHOT UEFI]
[rEFInd Boot Manager]

Perhaps there is a quicker and easier method than mine.


Solution

  • A better solution for getting output the firmware descriptions without trailing spaces is:

    @echo off & setlocal EnableExtensions DisableDelayedExpansion
    (for /F "tokens=1*" %%I in ('%SystemRoot%\System32\bcdedit.exe /enum FIRMWARE ^| %SystemRoot%\System32\findstr.exe /B /L "description"') do set "Description=%%J" & call :Output) & pause & exit /B
    :Output
    if "%Description:~-1%" == " " (set "Description=%Description:~0,-1%" & goto Output) else echo [%Description%]& goto :EOF
    

    The batch file must be run as administrator as otherwise nothing is output because of bcdedit.exe requires the elevated privileges of a local administrator for opening the boot configuration data store.

    The first command line defined completely the required execution environment which is:

    1. Command echo mode turned off.
    2. Command extensions enabled as required for this batch file.
    3. Delayed variable expansion disabled as not needed and required for processing also correct firmware descriptions with one or more ! inside.

    The second command line is the main code of the batch file on a single line for a minimum of file system accesses during the execution of the batch file.

    There is executed first in background by for /F:

    %ComSpec% /c %SystemRoot%\System32\bcdedit.exe /enum FIRMWARE | %SystemRoot%\System32\findstr.exe /B /L "description"
    

    The redirection operator | must be escaped with ^ in the FOR /F command line for being interpreted literally by cmd.exe processing the batch file. The command process started in background gets passed only the vertical bar character and interprets it for that reason as redirection operator.

    The output of bcdedit.exe is redirected to findstr.exe which filters out all lines not beginning case-sensitive with the string description.

    That filtered output of bcdedit.exe is captured by cmd.exe processing the batch file and processed line by line by FOR after the started cmd.exe closed itself after execution of the two executables.

    Each captured line is split up into two substrings. The first one is description which is assigned to the specified loop variable I. The string after the spaces after description is assigned with all its spaces including the trailing spaces to the next loop variable J according to the ASCII table.

    This string is assigned to the environment variable Description before a subroutine with name Output is called which processes the description further and finally outputs the description. It is expected by this code that no firmware description contains ever one or more double quotes.

    The subroutine compares the last character of the current string value of the environment variable Description with a space. If that condition is true, the environment variable Description is redefined without the trailing space and the last character check is done once again by continuation of the batch file processing on the same line by using command GOTO instead of the not existing next line. The ELSE branch of the IF condition in the subroutine Output is run only if the last character of the current description is not a space character and outputs the trimmed description in square brackets. Then the subroutine is exited with goto :EOF and batch file processing continues with processing the next captured line by FOR /F.

    Once the FOR /F loop finished processing all lines, the command PAUSE is executed for halting the batch file processing until the user presses a key and next exit /B is executed to exit the processing of the batch file without running the commands in the subroutine Output once more.

    To understand the commands used and how they work, open a command prompt window, execute there the following commands, and read the displayed help pages for each command, entirely and carefully.

    • bcdedit /?
    • bcdedit /enum /?
    • call /?
    • echo /?
    • exit /?
    • findstr /?
    • for /?
    • goto /?
    • if /?
    • pause /?
    • set /?
    • setlocal /?

    See also: