I'm working on batch file and export to text file. Seem all of them is ok, but when i open text file, many new lines break. So, i want to remove of them.
@echo OFF
setlocal EnableDelayedExpansion
(
systeminfo |findstr /c:"Host Name" /c:"OS Name" /c:"OS Version" /c:"Original Install Date" /c:"System Manufacturer" /c:"System Model" /c:"System Type" /c:"Total Physical Memory"
wmic bios get serialnumber /Format:list | more | findstr .
wmic cpu get name /Format:list | more | findstr .
echo=%userdomain%\%username%
)> %ComputerName%.txt
The result text file is ok, but still many new lines break, i want to remove of them
Host Name: PGV-PF165HNN
OS Name: Microsoft Windows 10 Pro
OS Version: 10.0.18363 N/A Build 18363
Original Install Date: 7/22/2019, 6:28:01 PM
System Manufacturer: LENOVO
System Model: 20JM0009US
System Type: x64-based PC
BIOS Version: LENOVO N1QET87W (1.62 ), 2/27/2020
Total Physical Memory: 8,072 MB
SerialNumber=PF165HNN
Name=Intel(R) Core(TM) i5-6300U CPU @ 2.40GHz
WINDOM1\brian.lee
The OS language dependent output of
%SystemRoot%\System32\systeminfo.exe
is character encoded in ASCII/ANSI/OEM which means one byte per character using the code page as displayed on running in a command prompt windowchcp
. The code page depends on the country (region) configured for the account used to run the batch file. The code page does not really matter as long as the data of interest do not contain characters with a code value greater 127 (non-ASCII character).The output of
systeminfo
filtered byfindstr
is in binary with hexadecimal offset in file left to colon, hexadecimal values of the bytes, and their ASCII representation after the semicolon:The output of
%SystemRoot%\System32\wbem\wmic.exe
is always Unicode encoded using UTF-16 Little Endian encoding with byte order mark (BOM). So the output by the two usedwmic
command lines is with two bytes per character.The command line
wmic bios get serialnumber /Format:list
produces in binary the output:The first two bytes
FF FE
is the byte order mark for UTF-16 Little Endian. Each ASCII character is encoded with two bytes (16 bits) with high byte having value 0. The newline characters are carriage return (0D 00) and line-feed (0A 00). There are two empty lines output first, then the line with the data of interest, and finally once again two empty lines.The command line
wmic cpu get name
produces in binary the output:The Unicode output is redirected by
cmd.exe
processing the batch file tomore
which outputs the lines now with one byte per character. But Windows command processor has a bug on interpreting UTF-16 LE encoded lines as it can be seen on using the following command line:The file
output.txt
contains the binary bytes:Each Unicode encoded carriage return + line-feed (0D 00 0A 00) becomes ASCII encoded carriage return + carriage return + line-feed (0D 0D 0A).
That is the real problem here. The additional carriage return results on using regular expression search string
.
to match all lines with at least one character that also the empty lines are matched by this regular expression search string on output converted not correct from Unicode to ASCII.It depends on used text editor how the not valid sequence of newline characters are interpreted. Most text editors interpret the carriage return without line-feed as line termination, but
findstr
does not do that.One solution is explicitly searching for the line which contains the data of interest.
The data written into file
%ComputerName%.txt
is completely encoded in ASCII with everywhere used just0D 0A
as line termination.Some additional information about small changes on code:
more
is omitted as not really necessary. The not correct conversion from Unicode to ASCII is done by Windows command processorcmd.exe
.cmd.exe
has not to search for the executables using the values of the environment variablesPATHEXT
andPATH
./Format:list
is replaced by option/VALUE
which results in same output./L
to explicitly instructfindstr
to run a literal search although that is the default on using option/C:
.An even better batch file code would be:
The additional data determined with WMIC and output with ECHO are written into the text file in same format as the output of
systeminfo
.Attention: The last
echo
command line is not safe in case of value of environment variableUSERDOMAIN
or of environment variableUSERNAME
contains)
or&
. 100% safe would be: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.
echo /?
endlocal /?
findstr /?
for /?
if /?
setlocal /?
systeminfo /?
wmic /?
wmic bios /?
wmic bios get /?
wmic cpu /?
wmic cpu get /?