Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

diskpart does not process script correctly when executed from CreateProcess()

diskpart "myScript.txt":

select disk 1
convert dynamic noerr
select disk 2
convert dynamic noerr
create volume stripe disk=1,2 noerr
assign letter=X noerr

.
.

When running from the command prompt: diskpart /s myScript.txt it works as expected.

However, when run using win api's CreateProcess() both the convert commands do work but when it gets to
create volume, it displays:

"The arguments you specified for this command are not valid"

. .

Now, to make things more interesting:
If the script is executed again from CreateProcess() a 2nd time (given the disks are now converted and it gives a correct error for the convert comamnds), when it gets to the create volume, it does work.

This makes me think it has something do with the disks and or executable?

Any point in the right direction is appreciated as this is very confusing. Thanks.

STARTUPINFO si;
PROCESS_INFORMATION pi;
ZeroMemory(&si, sizeof(si));
ZeroMemory(&pi, sizeof(pi));
si.cb = sizeof(si);
strncpy( command, "diskpart.exe /s myScript.txt", (sizeof(command) - 1) );  

             CreateProcess( "c:\\WINDOWS\\system32\\diskpart.exe",
                             command,
                             NULL,
                             NULL,
                             TRUE,
                             0,
                             NULL,
                             NULL,
                             &si,
                             &pi ) );

end original question________________________________________________________

EDIT:
Updates and more info:

  • Added about 15 - 20 seconds worth of delay before create volume command, still got the same error message.

  • Also, split the work into two scripts, with two calls to CreateProcess(). On the second script, just calling "create volume" and assign, it hung for a while and then came back with a "this command cannot be completed at this time"..or something to the effect.

  • Another thing to note: On the first script, putting them into dynamic, it was running about twice as slow compared to running with command prompt.

Maybe should just run the whole thing twice (with errors on the second run) as that did work

EDIT2
The 2 scripts is now working, or worked when I tried it again. Not sure why it didn't work the first time.

like image 456
T.T.T. Avatar asked Jan 09 '15 17:01

T.T.T.


2 Answers

Because your script works the second time through it seems the most likely cause is timing related -- The volumes are not ready by the time the create volume command is executed.

Based on that assumption:

You can add a detail disk command before the create volume command to find out the state of the disk. That will tell you something about the current state of the disk. Select the first disk as well to show its details too if disk 2 doesn't show you anything interesting. The information you get from this is likely to be helpful.

As for actually resolving the problem, introducing a delay by taking the disks online and offline may help. For example:

select disk 1
convert dynamic
select disk 2
convert dynamic
select disk 1
offline disk
select disk 2
offline disk
select disk 1
online disk
select disk 2
online disk
create volume stripe disk=1,2
assign letter=X
like image 120
janm Avatar answered Sep 19 '22 01:09

janm


Here is an excerpt of what http://msdn.microsoft.com/en-us/library/windows/desktop/ms682425%28v=vs.85%29.aspx says about the first parameter:

The lpApplicationName parameter can be NULL. In that case, the module name must be the first white space–delimited token in the lpCommandLine string.

If the executable module is a 16-bit application, lpApplicationName should be NULL, and the string pointed to by lpCommandLine should specify the executable module as well as its arguments.

given the above, Suggest:
(first, assure command[] buffer is plenty large enough for the following)
(may have to add the path for the 'myStript.txt)
(may be necessary to add some wait time before calling CreateProcess() 
 to assure the prior commands have completed.

strncpy( command, "c:\\Windows\\System32\\diskpart.exe /s myScript.txt", (sizeof(command) - 1) );  

CreateProcess(  NULL,
                command,
                NULL,
                NULL,
                TRUE,
                0,
                NULL,
                NULL,
                &si,
                &pi ) );
like image 41
user3629249 Avatar answered Sep 18 '22 01:09

user3629249