/// <summary> /// Executes an Android Sdk tool and returns a result. The result is based on a function of the command output. /// </summary> public static Task <TResult> ExecuteToolAsync <TResult> (string exe, Func <string, TResult> result, CancellationToken token, Action <Process>?onStarted = null) { var tcs = new TaskCompletionSource <TResult> (); var log = new StringWriter(); var error = new StringWriter(); var psi = new ProcessStartInfo(exe); psi.CreateNoWindow = true; psi.RedirectStandardInput = onStarted != null; var processTask = ProcessUtils.StartProcess(psi, log, error, token, onStarted); var exeName = Path.GetFileName(exe); processTask.ContinueWith(t => { var output = log.ToString(); var errorOutput = error.ToString(); log.Dispose(); error.Dispose(); if (t.IsCanceled) { tcs.TrySetCanceled(); return; } if (t.IsFaulted) { tcs.TrySetException(t.Exception?.Flatten()?.InnerException ?? t.Exception !); return; } if (t.Result == 0) { tcs.TrySetResult(result != null ? result(output) : default(TResult) !); } else { var errorMessage = !string.IsNullOrEmpty(errorOutput) ? errorOutput : output; errorMessage = string.IsNullOrEmpty(errorMessage) ? $"`{exeName}` returned non-zero exit code" : $"{t.Result} : {errorMessage}"; tcs.TrySetException(new InvalidOperationException(errorMessage)); } }, TaskContinuationOptions.ExecuteSynchronously); return(tcs.Task); }
void FixOwnership(List <string>?paths) { if (!need_chown || paths == null || paths.Count == 0) { return; } var stdout = new StringWriter(); var stderr = new StringWriter(); var args = new List <string> { QuoteString(sudo_user !) }; foreach (string p in paths) { args.Add(QuoteString(p)); } var psi = new ProcessStartInfo(OS.IsMac ? "/usr/sbin/chown" : "/bin/chown") { CreateNoWindow = true, Arguments = String.Join(" ", args), }; Logger(TraceLevel.Verbose, $"Changing filesystem object ownership: {psi.FileName} {psi.Arguments}"); Task <int> chown_task = ProcessUtils.StartProcess(psi, stdout, stderr, System.Threading.CancellationToken.None); if (chown_task.Result != 0) { Logger(TraceLevel.Warning, $"Failed to change ownership of filesystem object(s)"); Logger(TraceLevel.Verbose, $"standard output: {stdout}"); Logger(TraceLevel.Verbose, $"standard error: {stderr}"); } string QuoteString(string p) { return($"\"{p}\""); } } }