public Task StartAsync(Tool tool, ITorSharpProxy proxy)
        {
            IntPtr desktopHandle = WindowsUtility.CreateDesktop(DesktopName);

            // embrace the madness -- it seems Windows always wants exactly one instance of "ctfmon.exe" in the new desktop
            var ctfmonStartInfo = new ProcessStartInfo {
                FileName = "ctfmon.exe", WorkingDirectory = "."
            };

            WindowsApi.PROCESS_INFORMATION ctfmonProcess = WindowsUtility.CreateProcess(proxy, ctfmonStartInfo, DesktopName);
            AssociateWithJob(ctfmonProcess, false);

            // start the desired process
            var arguments = string.Join(" ", tool.Settings.GetArguments(tool));
            var startInfo = new ProcessStartInfo
            {
                FileName         = tool.ExecutablePath,
                Arguments        = arguments,
                WorkingDirectory = tool.WorkingDirectory
            };

            WindowsApi.PROCESS_INFORMATION targetProcess = WindowsUtility.CreateProcess(proxy, startInfo, DesktopName);
            AssociateWithJob(targetProcess, true);

            return(Task.FromResult((object)null));
        }
Exemple #2
0
        public static WindowsApi.PROCESS_INFORMATION CreateProcess(ITorSharpProxy proxy, ProcessStartInfo startInfo, string desktopName = null, int?millisecondsToWait = 100)
        {
            // Source: https://stackoverflow.com/a/59387440/3286975
            var startupInfo = new WindowsApi.STARTUPINFO();

            startupInfo.cb        = Marshal.SizeOf(startupInfo);
            startupInfo.lpDesktop = desktopName;

            var processInformation = new WindowsApi.PROCESS_INFORMATION();

            string command = startInfo.FileName + " " + startInfo.Arguments;

            WindowsApi.SECURITY_ATTRIBUTES saAttr = new WindowsApi.SECURITY_ATTRIBUTES
            {
                nLength              = (uint)Marshal.SizeOf(typeof(WindowsApi.SECURITY_ATTRIBUTES)),
                bInheritHandle       = 0x1,
                lpSecurityDescriptor = IntPtr.Zero
            };

            WindowsApi.CreatePipe(ref out_read, ref out_write, ref saAttr, 0);
            WindowsApi.CreatePipe(ref err_read, ref err_write, ref saAttr, 0);

            WindowsApi.SetHandleInformation(out_read, HANDLE_FLAG_INHERIT, 0);
            WindowsApi.SetHandleInformation(err_read, HANDLE_FLAG_INHERIT, 0);

            bool result = WindowsApi.CreateProcess(null,
                                                   command,
                                                   IntPtr.Zero,
                                                   IntPtr.Zero,
                                                   true,
                                                   WindowsApi.NORMAL_PRIORITY_CLASS,
                                                   IntPtr.Zero,
                                                   startInfo.WorkingDirectory,
                                                   ref startupInfo,
                                                   ref processInformation);

            var thread = new Thread(() => RedirectStd(proxy));

            thread.Start();

            if (result)
            {
                if (millisecondsToWait.HasValue)
                {
                    WindowsApi.WaitForInputIdle(processInformation.hProcess, (uint)millisecondsToWait.Value);
                }

                WindowsApi.CloseHandle(processInformation.hThread);
                return(processInformation);
            }

            return(new WindowsApi.PROCESS_INFORMATION());
        }
Exemple #3
0
        private static void RedirectStd(ITorSharpProxy proxy)
        {
            // Source: https://stackoverflow.com/a/59387440/3286975

            byte[] out_buf = new byte[BUFSIZE];
            byte[] err_buf = new byte[BUFSIZE];

            int dwRead = 0;

            string out_str = "";
            string err_str = "";

            bool isOutputSet = proxy.GetHandler(true) != null;
            bool isErrorSet  = proxy.GetHandler(false) != null;

            while (true)
            {
                bool bSuccess;

                if (isOutputSet)
                {
                    bSuccess = WindowsApi.ReadFile(out_read, out_buf, BUFSIZE, ref dwRead, IntPtr.Zero);
                    if (!bSuccess || dwRead == 0)
                    {
                        break;
                    }

                    out_str += System.Text.Encoding.Default.GetString(out_buf);
                    out_str  = PushCallback(proxy, out_str, true);
                }

                if (isErrorSet)
                {
                    bSuccess = WindowsApi.ReadFile(out_read, err_buf, BUFSIZE, ref dwRead, IntPtr.Zero);
                    if (!bSuccess || dwRead == 0)
                    {
                        break;
                    }

                    err_str += System.Text.Encoding.Default.GetString(err_buf);
                    err_str  = PushCallback(proxy, err_str, true);
                }
            }

            WindowsApi.CloseHandle(out_read);
            WindowsApi.CloseHandle(err_read);
            WindowsApi.CloseHandle(out_write);
            WindowsApi.CloseHandle(err_write);
        }
Exemple #4
0
        private static string PushCallback(ITorSharpProxy proxy, string str, bool isOutStream)
        {
            var lines = str.Split();

            foreach (var line in lines)
            {
                var instance = (DataReceivedEventArgs)Activator.CreateInstance(typeof(DataReceivedEventArgs), line);
                if (isOutStream)
                {
                    ((TorSharpProxy)proxy).HandleOnOutput(null, instance);
                }
                else
                {
                    ((TorSharpProxy)proxy).HandleOnError(null, instance);
                }
            }

            return(lines.Last());
        }
Exemple #5
0
        public TorSharpProxyHostedService(
            IOptions <TriasConfiguration> triasConfiguration,
            IHttpClientFactory httpClientFactory,
            IIpGeolocation ipGeolocation,
            ILogger <TorSharpProxyHostedService> logger
            )
        {
            _triasConfiguration = triasConfiguration;
            _httpClientFactory  = httpClientFactory;
            _ipGeolocation      = ipGeolocation;
            _logger             = logger;
            var config = triasConfiguration.Value;

            _proxy = new TorSharpProxy(config.TorSharpSettings);
            var proxyHttpClientHandler = new HttpClientHandler
            {
                Proxy = new WebProxy(new Uri($"http://localhost:{config.TorSharpSettings.PrivoxySettings.Port}"))
            };

            _proxyHttpClient = new HttpClient(proxyHttpClientHandler);
        }
Exemple #6
0
 public static DataReceivedEventHandler GetHandler(this ITorSharpProxy proxy, bool isOutStream)
 {
     return((DataReceivedEventHandler)proxy.GetType()
            .GetField(isOutStream ? "OnOutput" : "OnError", BindingFlags.NonPublic | BindingFlags.Instance)?.GetValue(proxy));
 }
Exemple #7
0
        public Task StartAsync(Tool tool, ITorSharpProxy proxy)
        {
            // start the desired process
            var arguments            = string.Join(" ", tool.Settings.GetArguments(tool));
            var environmentVariables = tool.Settings.GetEnvironmentVariables(tool);
            var startInfo            = new ProcessStartInfo
            {
                FileName               = tool.ExecutablePath,
                Arguments              = arguments,
                WorkingDirectory       = tool.WorkingDirectory,
                RedirectStandardOutput = true,
                RedirectStandardError  = true,
                UseShellExecute        = false,
                CreateNoWindow         = true,
                WindowStyle            = ProcessWindowStyle.Hidden,
            };

            foreach (var pair in environmentVariables)
            {
                startInfo.EnvironmentVariables[pair.Key] = pair.Value;
            }

            var process = Process.Start(startInfo);

            var onOutput = proxy.GetHandler(true);

            if (onOutput != null)
            {
                process.OutputDataReceived += onOutput;
            }
            else
            {
                process.OutputDataReceived += (sender, e) =>
                {
                    Console.WriteLine(e.Data);
                }
            };

            var onError = proxy.GetHandler(false);

            if (onError != null)
            {
                process.ErrorDataReceived += onError;
            }
            else
            {
                process.ErrorDataReceived += (sender, e) =>
                {
                    Console.Error.WriteLine(e.Data);
                }
            };

            process.BeginOutputReadLine();
            process.BeginErrorReadLine();

            if (process == null)
            {
                throw new TorSharpException($"Unable to start the process '{tool.ExecutablePath}'.");
            }

            _processes.Add(process);

            return(CompletedTask);
        }