1 Востаннє редагувалося Betterthanyou (21.01.2022 13:46:18)

Тема: Виконати довгий код команд cmd за допомогою нового процесу

Потрібно виконати довгий код команд (віндовська консоль виконання команд) Windows commands за допомогою процесу створеного програмою (в C#), також від Windows commands потрібно отримати текстову відповідь.

Під "довгим кодом" я маю на увазі Windows commands код, що перевищує 1000 символів.

Приклад довгого коду, але це не важливо

Звичайно можна викликати ffmpeg.exe на без Windows commands, але в деяких файлах ще є інші команди які не виконаються без Windows commands

C:\Users\Oleksandr\source\repos\App\bin\Debug\FFMPEG\ffmpeg.exe ^
-i "E:\Downloads\69.mp4" ^
-i "E:\Downloads\75.mp4" ^
-i "E:\Downloads\80.mp4" ^
-i "E:\Downloads\24.mp4" ^
-i "E:\Downloads\50.mp4" ^
-i "E:\Downloads\25.mp4" ^
-i "E:\Downloads\33.mp4" ^
-i "E:\Downloads\29.mp4" ^
-i "E:\Downloads\9.mp4" ^
-i "E:\Downloads\20.mp4" ^
-i "E:\Downloads\99.mp4" ^
-i "E:\Downloads\43.mp4" ^
-i "E:\Downloads\18.mp4" ^
-i "E:\Downloads\19.mp4" ^
-i "E:\Downloads\10.mp4" ^
-i "E:\Downloads\86.mp4" ^
-i "E:\Downloads\28.mp4" ^
-i "E:\Downloads\36.mp4" ^
-i "E:\Downloads\67.mp4" ^
-i "E:\Downloads\12.mp4" ^
-i "E:\Downloads\65.mp4" ^
-i "E:\Downloads\7.mp4" ^
-i "E:\Downloads\47.mp4" ^
-i "E:\Downloads\30.mp4" ^
-i "E:\Downloads\15.mp4" ^
-i "E:\Downloads\11.mp4" ^
-i "E:\Downloads\54.mp4" ^
-i "E:\Downloads\22.mp4" ^
-filter_complex ^
"[0:v][1:v]xfade=transition=fade:duration=1:offset=19[vfade1]; ^
[vfade1][2:v]xfade=transition=fade:duration=1:offset=38[vfade2]; ^
[vfade2][3:v]xfade=transition=fade:duration=1:offset=57[vfade3]; ^
[vfade3][4:v]xfade=transition=fade:duration=1:offset=76[vfade4]; ^
[vfade4][5:v]xfade=transition=fade:duration=1:offset=95[vfade5]; ^
[vfade5][6:v]xfade=transition=fade:duration=1:offset=114[vfade6]; ^
[vfade6][7:v]xfade=transition=fade:duration=1:offset=133[vfade7]; ^
[vfade7][8:v]xfade=transition=fade:duration=1:offset=152[vfade8]; ^
[vfade8][9:v]xfade=transition=fade:duration=1:offset=171[vfade9]; ^
[vfade9][10:v]xfade=transition=fade:duration=1:offset=190[vfade10]; ^
[vfade10][11:v]xfade=transition=fade:duration=1:offset=209[vfade11]; ^
[vfade11][12:v]xfade=transition=fade:duration=1:offset=228[vfade12]; ^
[vfade12][13:v]xfade=transition=fade:duration=1:offset=247[vfade13]; ^
[vfade13][14:v]xfade=transition=fade:duration=1:offset=266[vfade14]; ^
[vfade14][15:v]xfade=transition=fade:duration=1:offset=285[vfade15]; ^
[vfade15][16:v]xfade=transition=fade:duration=1:offset=304[vfade16]; ^
[vfade16][17:v]xfade=transition=fade:duration=1:offset=323[vfade17]; ^
[vfade17][18:v]xfade=transition=fade:duration=1:offset=342[vfade18]; ^
[vfade18][19:v]xfade=transition=fade:duration=1:offset=361[vfade19]; ^
[vfade19][20:v]xfade=transition=fade:duration=1:offset=380[vfade20]; ^
[vfade20][21:v]xfade=transition=fade:duration=1:offset=399[vfade21]; ^
[vfade21][22:v]xfade=transition=fade:duration=1:offset=418[vfade22]; ^
[vfade22][23:v]xfade=transition=fade:duration=1:offset=437[vfade23]; ^
[vfade23][24:v]xfade=transition=fade:duration=1:offset=456[vfade24]; ^
[vfade24][25:v]xfade=transition=fade:duration=1:offset=475[vfade25]; ^
[vfade25][26:v]xfade=transition=fade:duration=1:offset=494[vfade26]; ^
[vfade26][27:v]xfade=transition=fade:duration=1:offset=513" "E:\Downloads\result_88.mp4"

(С#) код що нижче, працює з не великим кодом Windows commands за довжиною, підозрюю що щось переповнюється і тому великий за довжиною код Windows commands не працює, тобто програма зависає і дальше нічого не відбувається... Можете підказати в чому може бути проблема ?

            Process cmd = new Process();
            cmd.StartInfo.FileName = "cmd.exe";
            cmd.StartInfo.RedirectStandardInput = true;
            cmd.StartInfo.RedirectStandardOutput = true;
            cmd.StartInfo.CreateNoWindow = true;
            cmd.StartInfo.UseShellExecute = false;
            cmd.Start();

            cmd.StandardInput.WriteLine(command);//command - тут код Windows commands
            cmd.StandardInput.Flush();
            cmd.StandardInput.Close();
            cmd.WaitForExit();

            List<string> results = new List<string>();
            string str;            
            while ((str = cmd.StandardOutput.ReadLine()) != null)
            {
                results.Add(str);
            }
            return results;

Ще одна ідея виникла: створити bat файл, записати довгий код (Windows commands) в цей файл, і передати цей файл в процес який відкрив cmd (Windows commands).

...
cmd.StandardInput.WriteLine("E\...PATH...\file_with_windows_commands.bat");
...

Проблема в такому варіанті, що постійно строюється файл на реальному жорсткому диску (це повільно і не зручно, а також
потрібно постійно видаляти файл). Чи можна створити файл у оперативній пам'яті, та передати цей файл в cmd (Windows commands) Якщо так, то як ?

2 Востаннє редагувалося koala (21.01.2022 15:09:57)

Re: Виконати довгий код команд cmd за допомогою нового процесу

Ви виконуєте команду інтерпретатора, а потім переробляєте відео, і скаржитеся, що пару кілобайтів на диск писати довго? Серйозно?
В принципі, у Windows є відображені на пам'ять файли, але чи прочитає їх cmd - не певен. А також є FileOptions.DeleteOnClose. Тоді краще в %TEMP% їх створювати, але антивірус може лаятися.
Але в будь-якому разі запускати cmd.exe і передавати йому стрічку "ffmpeg.exe" замість одразу запустити ffmpeg.exe - не тойво.

Подякували: Betterthanyou, leofun012

3

Re: Виконати довгий код команд cmd за допомогою нового процесу

FYI: The maximum length of the string that you can use at the command prompt is 8191 characters.

Подякували: Betterthanyou, 0xDADA11C7, leofun013

4

Re: Виконати довгий код команд cmd за допомогою нового процесу

А ще є опція ffmpeg -filter_complex_script .

Подякували: Betterthanyou, leofun012

5

Re: Виконати довгий код команд cmd за допомогою нового процесу

Узагалі треба дивитися зсередини. Є CreateProcess, другий параметр якого може бути до 32,767 символів (включно з ім'ям процесу та останнім нулем). Це точно максимальне обмеження.
У C# обмеження ще жорсткіше - The length of the string assigned to the Arguments property must be less than 32,699.
Тому якщо лізе - створюйте одразу

cmd.StartInfo.FileName = "C:\Users\Oleksandr\source\repos\App\bin\Debug\FFMPEG\ffmpeg.exe";
cmd.StartInfo.Arguments = "багато-багато аргументів";
cmd.Start();

А якщо забагато - створюйте файл із DeleteOnClose і передавайте його аргументом до -filter_complex_script.

Подякували: Betterthanyou1

6

Re: Виконати довгий код команд cmd за допомогою нового процесу

koala написав:

Узагалі треба дивитися зсередини. Є CreateProcess, другий параметр якого може бути до 32,767 символів (включно з ім'ям процесу та останнім нулем). Це точно максимальне обмеження.
У C# обмеження ще жорсткіше - The length of the string assigned to the Arguments property must be less than 32,699.
Тому якщо лізе - створюйте одразу

cmd.StartInfo.FileName = "C:\Users\Oleksandr\source\repos\App\bin\Debug\FFMPEG\ffmpeg.exe";
cmd.StartInfo.Arguments = "багато-багато аргументів";
cmd.Start();

А якщо забагато - створюйте файл із DeleteOnClose і передавайте його аргументом до -filter_complex_script.

Цей варіант підійшов.

7

Re: Виконати довгий код команд cmd за допомогою нового процесу

В принципі, у Windows є відображені на пам'ять файли, але чи прочитає їх cmd - не певен.

Пане Коала, я вважаю, що ви їх неправильно розумієте, ці відображені на пам'ять файли. Вони відображаються на пам'ять для легшого доступа до данних, а не щоб не пов'язуватися з файлом на диску. Не пов'язані з файлом на диску існують лише засоби IPC штибу pipes, mailslots, etc а також файли на RAM диску.

8

Re: Виконати довгий код команд cmd за допомогою нового процесу

Дякую за уточнення. Я мав на увазі спільну пам'ять процесів, що в Windows зветься "непостійним (non-persisted) відображеним файлом", бо доступ до цієї пам'яті здійснюється так само як і до звичайного відображеного файлу. Я гадки не маю, чи можна якось згодувати cmd таку спільну пам'ять.

Подякували: 0xDADA11C71