Old 2nd July 2019, 12:44   #1
meoit
Member
 
Join Date: Oct 2014
Location: $DESKTOP
Posts: 90
Post Parse cmd.exe output in ini file for each item to RichEdit

I run batch file with command:

code:

ExecShellWait 'open' '"$SYSDIR\cmd.exe"' '/c "D:\MyDisks.cmd"' SW_HIDE



Content batch MyDisks.cmd file:

code:

@ECHO OFF
SETLOCAL EnableExtensions EnableDelayedExpansion
SET "InputFile=MyDisks.ini"
IF EXIST "%InputFile%" (DEL /f /q "%InputFile%")
FOR /F "skip=2 tokens=*" %%G IN ('
"WMIC PATH Win32_DiskDrive GET Caption,Index,Size /format:csv 2>NUL"
') DO (
@FOR /F "tokens=2,3,4 delims=," %%H IN ("%%G") DO (
SET "strCaption=%%H"
SET "strIndex=%%I"
SET "strSize=%%J"
>>"%InputFile%" CALL ECHO [Disk%%strIndex%%]
>>"%InputFile%" CALL ECHO Item=Index%%strIndex%% - %%strCaption%% (%%strSize%%^)
)
)
pause



Result MyDisks.ini :

code:

[Disk0]
Item=Index0 - Samsung EVO (232536803840)
[Disk1]
Item=Index1 - Adata USB Device (35718510080)



But I do not know how to parse MyDisks.ini file for each item to the RichEdit control.

I tried

ReadINIStr $0 'D:\MyDisks.ini' 'DiskZZZ' 'Item'

but not success

I need content in the RichEdit control same as:

code:

Index0 - Samsung EVO (232536803840)
Index1 - Adata USB Device (35718510080)



Please help me.

Thanks.
meoit is offline   Reply With Quote
Old 2nd July 2019, 16:44   #2
Anders
Moderator
 
Anders's Avatar
 
Join Date: Jun 2002
Location: ${NSISDIR}
Posts: 5,153
SET "InputFile=MyDisks.ini" is a relative path. Try a full path.

IntOp $PostCount $PostCount + 1
Anders is offline   Reply With Quote
Old 2nd July 2019, 23:04   #3
meoit
Member
 
Join Date: Oct 2014
Location: $DESKTOP
Posts: 90
Yes Anders.

I put MyDisks.cmd in D:\ location.
And the output of MyDisks.cmd which MyDisks.ini also in D:\ location
meoit is offline   Reply With Quote
Old 3rd July 2019, 16:32   #4
Anders
Moderator
 
Anders's Avatar
 
Join Date: Jun 2002
Location: ${NSISDIR}
Posts: 5,153
Your batch-file and ReadINIStr ... "Disk0" work just fine for me when I use full paths.

ExecShellWait '"$SYSDIR\cmd.exe"' should just be '$SYSDIR\cmd.exe' but I assume this is not the real issue.

IntOp $PostCount $PostCount + 1
Anders is offline   Reply With Quote
Old 3rd July 2019, 22:06   #5
meoit
Member
 
Join Date: Oct 2014
Location: $DESKTOP
Posts: 90
Smile

There are computers with 2 storage devices, 3 storage devices, 4 storage devices, ... So, How do we know how many devices that the computer has ?.

Quote:
Index0 - Samsung EVO (232536803840)

Index1 - Adata USB Device (35718510080)

Index2 - Samsung EVO 2 (232536803840)

Index3 - Adata USB Device 2 (35718510080)

Index4 - Samsung EVO 3 (232536803840)

Index5 - Adata USB Device 3 (35718510080)

.....
.....
......
.....

IndexN - Samsung EVO N (232536803840)

IndexN - Adata USB Device N (35718510080)

Last edited by meoit; 3rd July 2019 at 23:18.
meoit is offline   Reply With Quote
Old 3rd July 2019, 23:22   #6
Nutzzz
Member
 
Join Date: May 2007
Location: Orange County, CA, U.S.A.
Posts: 58
Quote:
Originally Posted by meoit View Post
There are computers with 2 devices, 3 devices, 4 devices, ... how do we know how many devices that the computer has ?.
If you could assume that the disk numbers are contiguous, you could just loop through them until the Errors flag is set. Though that's usually true, it's not always a safe assumption. Assuming this ini file isn't used for any other purpose, I would personally make the section name in square brackets use the %%G number instead of the disk number, and then contiguity would be guaranteed.

Spoiler:
code:
rem ...
SET "strCount=%%G"

SET "strCaption=%%H"

SET "strIndex=%%I"

SET "strSize=%%J"

>>"%InputFile%" CALL ECHO [Disk%%strCount%%]

>>"%InputFile%" CALL ECHO Item=Index%%strIndex%% - %%strCaption%% (%%strSize%%^)
rem ...



Assuming you've done that, you'd loop through them, e.g.:

Spoiler:
code:
!include LogicLib.nsh
# ...
StrCpy $R0 0
ClearErrors
${DoUntil} ${Errors}
ReadINIStr $0 'D:\MyDisks.ini' 'Disk$R0' 'Item'
${IfNot} ${Errors}
${AndIfNot} $0 == ""
# ...
${EndIf}
IntOp $R0 $R0 + 1
${Loop}
ClearErrors



* * * * *

If you need to keep the index as is for some reason, then you'd have to come up with a maximum number beyond which the number of drives is unreasonable. 16, maybe, for a consumer system, but if you might be installing on a server, even though usually you'd expect to find lots of drives hidden behind a RAID pool, theoretically you could have hundreds of disks in a bunch of JBODs, so let's say, 200?

e.g.:

code:
!include LogicLib.nsh
!define MAX_DRIVES 200
# ...
ClearErrors
${For} $R0 0 ${MAX_DRIVES}
ReadINIStr $0 'D:\MyDisks.ini' 'Disk$R0' 'Item'
${IfNot} ${Errors}
${AndIfNot} $0 == ""
# ...
${EndIf}
${Next}
ClearErrors

Nutzzz is offline   Reply With Quote
Old 4th July 2019, 05:30   #7
meoit
Member
 
Join Date: Oct 2014
Location: $DESKTOP
Posts: 90
Smile

Thanks Nutzzz.

I edited MyDisks.cmd to count devices as you told.

Quote:
@ECHO OFF
SETLOCAL EnableExtensions EnableDelayedExpansion
SET "InputFile=MyDisks.ini"
IF EXIST "%InputFile%" (DEL /f /q "%InputFile%")
SET /A "Total_Devices=0"
SET /A "Index=0"
@FOR /F "skip=2 tokens=*" %%G IN ('
"WMIC PATH Win32_DiskDrive GET Index /format:csv 2>NUL"
') DO (
SET /A "Total_Devices=Total_Devices+1"
SET /A "Index=Index+1"
>>"%InputFile%" CALL ECHO [Disk%%Index%%]
@FOR /F Tokens^=* %%A IN ('
"WMIC PATH Win32_DiskDrive GET Caption,Size /value 2>NUL"
') DO (
@FOR /F Tokens^=* %%H IN ("%%A") DO (>>"%InputFile%" CALL ECHO %%H)
)
)
>>"%InputFile%" CALL ECHO [Total Devices]
>>"%InputFile%" CALL ECHO Value=%%Total_Devices%%
PAUSE
Then, read MyDisks.ini

Quote:
ReadINIStr $R1 'D:\MyDisks.ini' 'Total Devices' 'Value'
ClearErrors
${For} $R0 0 $R1
ReadINIStr $0 'D:\MyDisks.ini' 'Disk$R0' 'Item'
${IfNot} ${Errors}
${AndIfNot} $0 == ""
MessageBox MB_OK|MB_USERICON '$0'
${EndIf}
${Next}
ClearErrors
But when open MyDisks.ini, I see it double result devices.

Quote:
[Disk1]
Caption=Samsung EVO
Size=232536803840
Caption=Adata USB Device
Size=35718510080
[Disk2]
Caption=Samsung EVO
Size=232536803840
Caption=Adata USB Device
Size=35718510080
[Total Devices]
Value=2
How to fix this?.
meoit is offline   Reply With Quote
Old 4th July 2019, 18:15   #8
Nutzzz
Member
 
Join Date: May 2007
Location: Orange County, CA, U.S.A.
Posts: 58
Quote:
Originally Posted by meoit View Post
But when open MyDisks.ini, I see it double result devices.
As I said, you can't assume the Index value is contiguous, and your new method doesn't resolve that issue. Even if the method was valid, you're missing a where clause to match up the current index with the appropriate caption and size.

Did the replacement section I gave you not work, or are you required to use the Index value for your sections?
Nutzzz is offline   Reply With Quote
Old 4th July 2019, 22:24   #9
meoit
Member
 
Join Date: Oct 2014
Location: $DESKTOP
Posts: 90
Yes, I need to use Index value and count devices. And I want to read the size, to converte to MB, GB in NSIS, don't handle size in MyDisks.cmd.
meoit is offline   Reply With Quote
Old 7th July 2019, 23:54   #10
meoit
Member
 
Join Date: Oct 2014
Location: $DESKTOP
Posts: 90
Thanks Nutzz.

I fixed code for myself.

Quote:
ReadINIStr $0 'D:\MyDisks.ini' 'Total Devices' 'Value'
IntOp $R1 $0 + 1
ClearErrors
${For} $R0 0 $R1
ReadINIStr $1 'D:\MyDisks.ini' 'Disk$R0' 'Index'
${If} $R0 != $1
ReadINIStr $2 'D:\MyDisks.ini' 'Disk$R0' 'Item'
MessageBox MB_OK|MB_USERICON '$0'
${EndIf}
${Next}
ClearErrors
Now, it is working so good.
meoit is offline   Reply With Quote
Old 8th July 2019, 17:15   #11
Nutzzz
Member
 
Join Date: May 2007
Location: Orange County, CA, U.S.A.
Posts: 58
Quote:
Originally Posted by meoit View Post
Thanks Nutzz.

I fixed code for myself.
We are still not communicating. The user could pull a drive and end up with a gap in the index values, e.g.:
Disk 0
Disk 1
Disk 3
Nutzzz is offline   Reply With Quote
Reply
Go Back   Winamp & Shoutcast Forums > Developer Center > NSIS Discussion

Thread Tools Search this Thread
Search this Thread:

Advanced Search
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off

Forum Jump