Esempio n. 1
0
        public Core(int unsecurePort, int securePort)
        {
            FiddlerApplication.SetAppDisplayName("DaX.Core");

            FiddlerApplication.OnNotification           += FiddlerApplication_OnNotification;
            FiddlerApplication.Log.OnLogString          += Log_OnLogString;
            FiddlerApplication.BeforeRequest            += FiddlerApplication_BeforeRequest;
            FiddlerApplication.OnReadResponseBuffer     += FiddlerApplication_OnReadResponseBuffer;
            FiddlerApplication.ResponseHeadersAvailable += FiddlerApplication_ResponseHeadersAvailable;
            FiddlerApplication.BeforeResponse           += FiddlerApplication_BeforeResponse;
            FiddlerApplication.AfterSessionComplete     += FiddlerApplication_AfterSessionComplete;


            Console.WriteLine(String.Format("Starting {0} ...", FiddlerApplication.GetVersionString()));

            CONFIG.IgnoreServerCertErrors = false;
            FiddlerApplication.Prefs.SetBoolPref("fiddler.network.streaming.abortifclientaborts", true);

            FiddlerCoreStartupFlags oFCSF = FiddlerCoreStartupFlags.Default;

            oFCSF = FiddlerCoreStartupFlags.Default & ~FiddlerCoreStartupFlags.RegisterAsSystemProxy;
            FiddlerApplication.Startup(unsecurePort, oFCSF);

            FiddlerApplication.Log.LogFormat("Created endpoint listening on port {0}", unsecurePort);

            FiddlerApplication.Log.LogFormat("Starting with settings: [{0}]", oFCSF);
            FiddlerApplication.Log.LogFormat("Gateway: {0}", CONFIG.UpstreamGateway.ToString());
            oSecureEndpoint = FiddlerApplication.CreateProxyEndpoint(securePort, true, sSecureEndpointHostname);
            if (null != oSecureEndpoint)
            {
                FiddlerApplication.Log.LogFormat("Created secure endpoint listening on port {0}, using a HTTPS certificate for '{1}'", securePort, sSecureEndpointHostname);
            }
        }
Esempio n. 2
0
        public void Start(object url)
        {
            bDone = false;
            FiddlerApplication.SetAppDisplayName("FiddlerCoreDemoApp");
            this.url = url.ToString();
            FiddlerApplication.OnNotification  += (object sender, NotificationEventArgs oNEA) => Console.WriteLine("** NotifyUser: "******"** LogString: " + oLEA.LogString);

            FiddlerApplication.Prefs.SetBoolPref("fiddler.network.streaming.abortifclientaborts", true);

            FiddlerApplication.BeforeRequest += FBeforeRequest;

            string sSAZInfo = "NoSAZ";

            Console.WriteLine(String.Format("Starting {0} ({1})...", FiddlerApplication.GetVersionString(), sSAZInfo));

            CONFIG.IgnoreServerCertErrors = true;

            int iPort = 8877;

            FiddlerApplication.Startup(iPort, true, true);

            oSecureEndpoint = FiddlerApplication.CreateProxyEndpoint(iSecureEndpointPort, true, sSecureEndpointHostname);
        }
Esempio n. 3
0
        public static void Main(string[] args)
        {
            // This is a workaround for known issue in .NET Core - https://github.com/dotnet/coreclr/issues/12668
            CultureInfo.DefaultThreadCurrentUICulture = new CultureInfo("en-US");

            //
            // It is important to understand that FiddlerCore calls event handlers on session-handling
            // background threads.  If you need to properly synchronize to the UI-thread (say, because
            // you're adding the sessions to a list view) you must call .Invoke on a delegate on the
            // window handle.
            //
            // If you are writing to a non-threadsafe data structure (e.g. List<>) you must
            // use a lock or other mechanism to ensure safety.
            //

            FiddlerApplication.Log.OnLogString += (object sender, LogEventArgs oLEA) =>
            {
                Console.WriteLine("** LogString: " + oLEA.LogString);
            };

            FiddlerApplication.BeforeRequest += (Session oS) =>
            {
                // In order to enable response tampering, buffering mode MUST
                // be enabled; this allows FiddlerCore to permit modification of
                // the response in the BeforeResponse handler rather than streaming
                // the response to the client as the response comes in.
                oS.bBufferResponse = false;
                lock (oAllSessions)
                {
                    oAllSessions.Add(oS);
                }

                // Set this property if you want FiddlerCore to automatically authenticate by
                // answering Digest/Negotiate/NTLM/Kerberos challenges itself
                // oS["X-AutoAuth"] = "(default)";

                /* If the request is going to our secure endpoint, we'll echo back the response.
                 *
                 * Note: This BeforeRequest is getting called for both our main proxy tunnel AND our secure endpoint,
                 * so we have to look at which Fiddler port the client connected to (pipeClient.LocalPort) to determine whether this request
                 * was sent to secure endpoint, or was merely sent to the main proxy tunnel (e.g. a CONNECT) in order to *reach* the secure endpoint.
                 *
                 * As a result of this, if you run the demo and visit https://localhost:7777 in your browser, you'll see
                 *
                 * Session list contains...
                 *
                 *  1 CONNECT http://localhost:7777
                 *  200                                         <-- CONNECT tunnel sent to the main proxy tunnel, port 8877
                 *
                 *  2 GET https://localhost:7777/
                 *  200 text/html                               <-- GET request decrypted on the main proxy tunnel, port 8877
                 *
                 *  3 GET https://localhost:7777/
                 *  200 text/html                               <-- GET request received by the secure endpoint, port 7777
                 */

                if ((oS.oRequest.pipeClient.LocalPort == iSecureEndpointPort) && (oS.hostname == sSecureEndpointHostname))
                {
                    oS.utilCreateResponseAndBypassServer();
                    oS.oResponse.headers.SetStatus(200, "Ok");
                    oS.oResponse["Content-Type"]  = "text/html; charset=UTF-8";
                    oS.oResponse["Cache-Control"] = "private, max-age=0";
                    oS.utilSetResponseBody("<html><body>Request for httpS://" + sSecureEndpointHostname + ":" + iSecureEndpointPort.ToString() + " received. Your request was:<br /><plaintext>" + oS.oRequest.headers.ToString());
                }
            };

            // The following event allows you to examine every response buffer read by Fiddler. Note that this isn't useful for the vast majority of
            // applications because the raw buffer is nearly useless; it's not decompressed, it includes both headers and body bytes, etc.
            //
            // This event is only useful for a handful of applications which need access to a raw, unprocessed byte-stream
            // FiddlerApplication.OnReadResponseBuffer += FiddlerApplication_OnReadResponseBuffer;

            /*
             * FiddlerApplication.BeforeResponse += (Session oS) =>
             * {
             *  Console.WriteLine($"{oS.id}:HTTP {oS.responseCode} for {oS.fullUrl}");
             *
             *  // Uncomment the following two statements to decompress/unchunk the
             *  // HTTP response and subsequently modify any HTTP responses to replace
             *  // instances of the word "Microsoft" with "Bayden". You MUST also
             *  // set bBufferResponse = true inside the beforeREQUEST method above.
             *  //
             *  // oS.utilDecodeResponse();
             *  // oS.utilReplaceInResponse("Microsoft", "Bayden");
             * };
             */

            FiddlerApplication.AfterSessionComplete += (Session oS) =>
            {
                int count;
                lock (oAllSessions)
                {
                    count = oAllSessions.Count;
                }

                Console.Title = ($"Session list contains: {count} sessions");
            };

            // Tell the system console to handle CTRL+C by calling our method that
            // gracefully shuts down the FiddlerCore.
            //
            // Note, this doesn't handle the case where the user closes the window with the close button.
            // See http://geekswithblogs.net/mrnat/archive/2004/09/23/11594.aspx for info on that...
            //
            Console.CancelKeyPress += new ConsoleCancelEventHandler(Console_CancelKeyPress);

            Console.WriteLine($"Starting {FiddlerApplication.GetVersionString()}...");

            // For the purposes of this demo, we'll forbid connections to HTTPS
            // sites that use invalid certificates. Change this from the default only
            // if you know EXACTLY what that implies.
            CONFIG.IgnoreServerCertErrors = false;

            // ... but you can allow a specific (even invalid) certificate by implementing and assigning a callback...
            // FiddlerApplication.OnValidateServerCertificate += CheckCert;

            FiddlerApplication.Prefs.SetBoolPref("fiddler.network.streaming.abortifclientaborts", true);

            // For forward-compatibility with updated FiddlerCore libraries, it is strongly recommended that you
            // start with the DEFAULT options and manually disable specific unwanted options.
            FiddlerCoreStartupFlags oFCSF = FiddlerCoreStartupFlags.Default;

            // E.g. If you want to add a flag, start with the .Default and "OR" the new flag on:
            // oFCSF = (oFCSF | FiddlerCoreStartupFlags.RegisterAsSystemProxy);

            // Uncomment the next line if you don't want to decrypt SSL traffic.
            // oFCSF = (oFCSF & ~FiddlerCoreStartupFlags.DecryptSSL);

            // NOTE: In the next line, you can pass 0 for the port (instead of 8877) to have FiddlerCore auto-select an available port
            int iPort = 8877;

            FiddlerApplication.Startup(iPort, oFCSF /*, upstreamGateway: "http=CorpProxy:80;https=SecureProxy:443;ftp=ftpGW:20"*/);

            FiddlerApplication.Log.LogFormat("Created endpoint listening on port {0}", iPort);

            FiddlerApplication.Log.LogFormat("Starting with settings: [{0}]", oFCSF);
            FiddlerApplication.Log.LogFormat("Gateway: {0}", CONFIG.UpstreamGateway.ToString());

            Console.WriteLine("Hit CTRL+C to end session.");

            // We'll also create a HTTPS listener, useful for when FiddlerCore is masquerading as a HTTPS server
            // instead of acting as a normal CERN-style proxy server.
            oSecureEndpoint = FiddlerApplication.CreateProxyEndpoint(iSecureEndpointPort, true, sSecureEndpointHostname);
            if (null != oSecureEndpoint)
            {
                FiddlerApplication.Log.LogFormat("Created secure endpoint listening on port {0}, using a HTTPS certificate for '{1}'", iSecureEndpointPort, sSecureEndpointHostname);
            }

            bool bDone = false;

            do
            {
                Console.WriteLine("\nEnter a command [C=Clear; D=Shutdown; E=Export cert to Desktop; L=List;\n\tG=Collect Garbage; T=Trust cert on Windows; S=Toggle Forgetful\n\tStreaming; Q=Quit]:");
                Console.Write(">");
                ConsoleKeyInfo cki = Console.ReadKey();
                Console.WriteLine();
                switch (Char.ToLower(cki.KeyChar))
                {
                case 'c':
                    lock (oAllSessions)
                    {
                        oAllSessions.Clear();
                    }

                    WriteCommandResponse("Clear...");
                    FiddlerApplication.Log.LogString("Cleared session list.");
                    break;

                case 'd':
                    FiddlerApplication.Log.LogString("FiddlerApplication::Shutdown.");
                    FiddlerApplication.Shutdown();
                    break;

                case 'e':
                    X509Certificate2 rootCert = CertMaker.GetRootCertificate();
                    if (rootCert == null)
                    {
                        FiddlerApplication.Log.LogString("Root certificate not found.");
                        break;
                    }

                    byte[] rootCertBytes = rootCert.Export(X509ContentType.Cert);
                    string rootCertPath  = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.DesktopDirectory), "FiddlerCoreRoot.cer");
                    File.WriteAllBytes(rootCertPath, rootCertBytes);
                    FiddlerApplication.Log.LogString("Root certificate exported successfully.");
                    break;

                case 'l':
                    WriteSessionList();
                    break;

                case 'g':
                    Console.WriteLine("Working Set:\t" + Environment.WorkingSet.ToString("n0"));
                    Console.WriteLine("Begin GC...");
                    GC.Collect();
                    Console.WriteLine("GC Done.\nWorking Set:\t" + Environment.WorkingSet.ToString("n0"));
                    break;

                case 'q':
                    bDone = true;
                    DoQuit();
                    break;

                case 't':
                    try
                    {
                        WriteCommandResponse("Result: " + CertMaker.trustRootCert().ToString());
                    }
                    catch (Exception eX)
                    {
                        WriteCommandResponse("Failed: " + eX.ToString());
                    }
                    break;

                // Forgetful streaming
                case 's':
                    bool bForgetful = !FiddlerApplication.Prefs.GetBoolPref("fiddler.network.streaming.ForgetStreamedData", false);
                    FiddlerApplication.Prefs.SetBoolPref("fiddler.network.streaming.ForgetStreamedData", bForgetful);
                    Console.WriteLine(bForgetful ? "FiddlerCore will immediately dump streaming response data." : "FiddlerCore will keep a copy of streamed response data.");
                    break;
                }
            } while (!bDone);
        }
        static void Main(string[] args)
        {
            List <Session> oAllSessions = new List <Session>();

            // <-- Personalize for your Application, 64 chars or fewer
            FiddlerApplication.SetAppDisplayName("FiddlerCoreDemoApp");

            #region AttachEventListeners
            //
            // It is important to understand that FiddlerCore calls event handlers on session-handling
            // background threads.  If you need to properly synchronize to the UI-thread (say, because
            // you're adding the sessions to a list view) you must call .Invoke on a delegate on the
            // window handle.
            //
            // If you are writing to a non-threadsafe data structure (e.g. List<t>) you must
            // use a Monitor or other mechanism to ensure safety.
            //

            // Simply echo notifications to the console.  Because Fiddler.CONFIG.QuietMode=true
            // by default, we must handle notifying the user ourselves.
            FiddlerApplication.OnNotification  += (object sender, NotificationEventArgs oNEA) => { Console.WriteLine("** NotifyUser: "******"** LogString: " + oLEA.LogString); };

            FiddlerApplication.BeforeRequest += delegate(Session oS)
            {
                // Console.WriteLine("Before request for:\t" + oS.fullUrl);
                // In order to enable response tampering, buffering mode MUST
                // be enabled; this allows FiddlerCore to permit modification of
                // the response in the BeforeResponse handler rather than streaming
                // the response to the client as the response comes in.
                oS.bBufferResponse = false;
                Monitor.Enter(oAllSessions);
                oAllSessions.Add(oS);
                Monitor.Exit(oAllSessions);

                // Set this property if you want FiddlerCore to automatically authenticate by
                // answering Digest/Negotiate/NTLM/Kerberos challenges itself
                // oS["X-AutoAuth"] = "(default)";

                /* If the request is going to our secure endpoint, we'll echo back the response.
                 *
                 * Note: This BeforeRequest is getting called for both our main proxy tunnel AND our secure endpoint,
                 * so we have to look at which Fiddler port the client connected to (pipeClient.LocalPort) to determine whether this request
                 * was sent to secure endpoint, or was merely sent to the main proxy tunnel (e.g. a CONNECT) in order to *reach* the secure endpoint.
                 *
                 * As a result of this, if you run the demo and visit https://localhost:7777 in your browser, you'll see
                 *
                 * Session list contains...
                 *
                 *  1 CONNECT http://localhost:7777
                 *  200                                         <-- CONNECT tunnel sent to the main proxy tunnel, port 8877
                 *
                 *  2 GET https://localhost:7777/
                 *  200 text/html                               <-- GET request decrypted on the main proxy tunnel, port 8877
                 *
                 *  3 GET https://localhost:7777/
                 *  200 text/html                               <-- GET request received by the secure endpoint, port 7777
                 */

                if ((oS.oRequest.pipeClient.LocalPort == iSecureEndpointPort) && (oS.hostname == sSecureEndpointHostname))
                {
                    oS.utilCreateResponseAndBypassServer();
                    oS.oResponse.headers.SetStatus(200, "Ok");
                    oS.oResponse["Content-Type"]  = "text/html; charset=UTF-8";
                    oS.oResponse["Cache-Control"] = "private, max-age=0";
                    oS.utilSetResponseBody("<html><body>Request for httpS://" + sSecureEndpointHostname + ":" + iSecureEndpointPort.ToString() + " received. Your request was:<br /><plaintext>" + oS.oRequest.headers.ToString());
                }
            };

            /*
             *  // The following event allows you to examine every response buffer read by Fiddler. Note that this isn't useful for the vast majority of
             *  // applications because the raw buffer is nearly useless; it's not decompressed, it includes both headers and body bytes, etc.
             *  //
             *  // This event is only useful for a handful of applications which need access to a raw, unprocessed byte-stream
             *  Fiddler.FiddlerApplication.OnReadResponseBuffer += new EventHandler<RawReadEventArgs>(FiddlerApplication_OnReadResponseBuffer);
             */

            /*
             * Fiddler.FiddlerApplication.BeforeResponse += delegate(Fiddler.Session oS) {
             *  // Console.WriteLine("{0}:HTTP {1} for {2}", oS.id, oS.responseCode, oS.fullUrl);
             *
             *  // Uncomment the following two statements to decompress/unchunk the
             *  // HTTP response and subsequently modify any HTTP responses to replace
             *  // instances of the word "Microsoft" with "Bayden". You MUST also
             *  // set bBufferResponse = true inside the beforeREQUEST method above.
             *  //
             *  //oS.utilDecodeResponse(); oS.utilReplaceInResponse("Microsoft", "Bayden");
             * };*/

            FiddlerApplication.AfterSessionComplete += (Session oS) =>
            {
                Console.Title = ($"Session list contains: {oAllSessions.Count.ToString()} sessions.");
            };

            // Tell the system console to handle CTRL+C by calling our method that
            // gracefully shuts down the FiddlerCore.
            //
            // Note, this doesn't handle the case where the user closes the window with the close button.
            // See http://geekswithblogs.net/mrnat/archive/2004/09/23/11594.aspx for info on that...
            //
            Console.CancelKeyPress += new ConsoleCancelEventHandler(Console_CancelKeyPress);
            #endregion AttachEventListeners

            string sSAZInfo = "NoSAZ";

            Console.WriteLine(String.Format("Starting {0} ({1})...", FiddlerApplication.GetVersionString(), sSAZInfo));

            // For the purposes of this demo, we'll forbid connections to HTTPS
            // sites that use invalid certificates. Change this from the default only
            // if you know EXACTLY what that implies.
            CONFIG.IgnoreServerCertErrors = false;

            // ... but you can allow a specific (even invalid) certificate by implementing and assigning a callback...
            // FiddlerApplication.OnValidateServerCertificate += new System.EventHandler<ValidateServerCertificateEventArgs>(CheckCert);

            FiddlerApplication.Prefs.SetBoolPref("fiddler.network.streaming.abortifclientaborts", true);

            // NOTE: In the next line, you can pass 0 for the port (instead of 8877) to have FiddlerCore auto-select an available port
            ushort iPort = 8877;

            FiddlerCoreStartupSettings startupSettings =
                new FiddlerCoreStartupSettingsBuilder()
                .ListenOnPort(iPort)
                .RegisterAsSystemProxy()
                .DecryptSSL()
                //.AllowRemoteClients()
                //.ChainToUpstreamGateway()
                //.MonitorAllConnections()
                //.HookUsingPACFile()
                .CaptureLocalhostTraffic()
                //.CaptureFTP()
                .OptimizeThreadPool()
                //.SetUpstreamGatewayTo("http=CorpProxy:80;https=SecureProxy:443;ftp=ftpGW:20")
                .Build();

            // *******************************
            // Important HTTPS Decryption Info
            // *******************************
            // When FiddlerCoreStartupSettingsBuilder.DecryptSSL() is called, you must include either
            //
            //     MakeCert.exe
            //
            // *or*
            //
            //     CertMaker.dll
            //     BCMakeCert.dll
            //
            // ... in the folder where your executable and FiddlerCore.dll live. These files
            // are needed to generate the self-signed certificates used to man-in-the-middle
            // secure traffic. MakeCert.exe uses Windows APIs to generate certificates which
            // are stored in the user's \Personal\ Certificates store. These certificates are
            // NOT compatible with iOS devices which require specific fields in the certificate
            // which are not set by MakeCert.exe.
            //
            // In contrast, CertMaker.dll uses the BouncyCastle C# library (BCMakeCert.dll) to
            // generate new certificates from scratch. These certificates are stored in memory
            // only, and are compatible with iOS devices.

            FiddlerApplication.Startup(startupSettings);

            FiddlerApplication.Log.LogFormat("Created endpoint listening on port {0}", iPort);

            FiddlerApplication.Log.LogFormat("Gateway: {0}", CONFIG.UpstreamGateway.ToString());

            Console.WriteLine("Hit CTRL+C to end session.");

            // We'll also create a HTTPS listener, useful for when FiddlerCore is masquerading as a HTTPS server
            // instead of acting as a normal CERN-style proxy server.
            oSecureEndpoint = FiddlerApplication.CreateProxyEndpoint(iSecureEndpointPort, true, sSecureEndpointHostname);
            if (null != oSecureEndpoint)
            {
                FiddlerApplication.Log.LogFormat("Created secure endpoint listening on port {0}, using a HTTPS certificate for '{1}'", iSecureEndpointPort, sSecureEndpointHostname);
            }

            bool bDone = false;
            do
            {
                Console.WriteLine("\nEnter a command [C=Clear; L=List; G=Collect Garbage; W=write SAZ; R=read SAZ;\n\tS=Toggle Forgetful Streaming; T=Trust Root Certificate; Q=Quit]:");
                Console.Write(">");
                ConsoleKeyInfo cki = Console.ReadKey();
                Console.WriteLine();
                switch (Char.ToLower(cki.KeyChar))
                {
                case 'c':
                    Monitor.Enter(oAllSessions);
                    oAllSessions.Clear();
                    Monitor.Exit(oAllSessions);
                    WriteCommandResponse("Clear...");
                    FiddlerApplication.Log.LogString("Cleared session list.");
                    break;

                case 'd':
                    FiddlerApplication.Log.LogString("FiddlerApplication::Shutdown.");
                    FiddlerApplication.Shutdown();
                    break;

                case 'l':
                    WriteSessionList(oAllSessions);
                    break;

                case 'g':
                    Console.WriteLine("Working Set:\t" + Environment.WorkingSet.ToString("n0"));
                    Console.WriteLine("Begin GC...");
                    GC.Collect();
                    Console.WriteLine("GC Done.\nWorking Set:\t" + Environment.WorkingSet.ToString("n0"));
                    break;

                case 'q':
                    bDone = true;
                    DoQuit();
                    break;

                case 'r':

                    WriteCommandResponse("This demo was compiled without SAZ_SUPPORT defined");
                    break;

                case 'w':

                    WriteCommandResponse("This demo was compiled without SAZ_SUPPORT defined");
                    break;

                case 't':
                    try
                    {
                        WriteCommandResponse("Result: " + Fiddler.CertMaker.trustRootCert().ToString());
                    }
                    catch (Exception eX)
                    {
                        WriteCommandResponse("Failed: " + eX.ToString());
                    }
                    break;

                // Forgetful streaming
                case 's':
                    bool bForgetful = !FiddlerApplication.Prefs.GetBoolPref("fiddler.network.streaming.ForgetStreamedData", false);
                    FiddlerApplication.Prefs.SetBoolPref("fiddler.network.streaming.ForgetStreamedData", bForgetful);
                    Console.WriteLine(bForgetful ? "FiddlerCore will immediately dump streaming response data." : "FiddlerCore will keep a copy of streamed response data.");
                    break;
                }
            } while (!bDone);
        }
Esempio n. 5
0
File: Form1.cs Progetto: XEonAX/DaX
        private void button1_Click(object btnsender, EventArgs e)
        {
            List <Fiddler.Session> oAllSessions = new List <Fiddler.Session>();

            // <-- Personalize for your Application, 64 chars or fewer
            FiddlerApplication.SetAppDisplayName("FiddlerDaX");

            #region AttachEventListeners
            FiddlerApplication.OnNotification += (sender, oNEA) =>
            {
                Console.WriteLine("** NotifyUser: "******"** LogString: " + oLEA.LogString);
            };

            FiddlerApplication.BeforeRequest += (oS) =>
            {
                oS["X-OverrideGateway"] = "127.0.0.1:8888";
                oS.bBufferResponse      = false;
                Monitor.Enter(oAllSessions);
                oAllSessions.Add(oS);
                Monitor.Exit(oAllSessions);

                // Set this property if you want FiddlerCore to automatically authenticate by
                // answering Digest/Negotiate/NTLM/Kerberos challenges itself
                // oS["X-AutoAuth"] = "(default)";

                /* If the request is going to our secure endpoint, we'll echo back the response.
                 *
                 * Note: This BeforeRequest is getting called for both our main proxy tunnel AND our secure endpoint,
                 * so we have to look at which Fiddler port the client connected to (pipeClient.LocalPort) to determine whether this request
                 * was sent to secure endpoint, or was merely sent to the main proxy tunnel (e.g. a CONNECT) in order to *reach* the secure endpoint.
                 *
                 * As a result of this, if you run the demo and visit https://localhost:7777 in your browser, you'll see
                 *
                 * Session list contains...
                 *
                 *  1 CONNECT http://localhost:7777
                 *  200                                         <-- CONNECT tunnel sent to the main proxy tunnel, port 8877
                 *
                 *  2 GET https://localhost:7777/
                 *  200 text/html                               <-- GET request decrypted on the main proxy tunnel, port 8877
                 *
                 *  3 GET https://localhost:7777/
                 *  200 text/html                               <-- GET request received by the secure endpoint, port 7777
                 */

                //if ((oS.oRequest.pipeClient.LocalPort == iSecureEndpointPort) && (oS.hostname == sSecureEndpointHostname))
                //{
                //    oS.utilCreateResponseAndBypassServer();
                //    oS.oResponse.headers.SetStatus(200, "Ok");
                //    oS.oResponse["Content-Type"] = "text/html; charset=UTF-8";
                //    oS.oResponse["Cache-Control"] = "private, max-age=0";
                //    oS.utilSetResponseBody("<html><body>Request for httpS://" + sSecureEndpointHostname + ":" + iSecureEndpointPort.ToString() + " received. Your request was:<br /><plaintext>" + oS.oRequest.headers.ToString());
                //}
            };

            Fiddler.FiddlerApplication.OnReadResponseBuffer += FiddlerApplication_OnReadResponseBuffer;



            FiddlerApplication.ResponseHeadersAvailable += oS =>
            {
                Console.WriteLine("{0}:HTTP {1} for {2}", oS.id, oS.responseCode, oS.fullUrl);
                var contentlength = oS.ResponseHeaders["Content-Length"];
                if (!string.IsNullOrWhiteSpace(contentlength) && int.Parse(contentlength) > 100000)
                {
                    dgv.BeginInvoke((Action)(() =>
                    {
                        sessionDS.SessionTable.AddSessionTableRow(oS.url, int.Parse(contentlength), oS);
                    }));
                }
                else
                {
                    dgv.BeginInvoke((Action)(() =>
                    {
                        sessionDS.SessionTable.AddSessionTableRow(oS.url, -1, oS);
                    }));
                }
            };
            FiddlerApplication.BeforeResponse += (oS) =>
            {
                if (oS.oFlags.ContainsKey("dax_id"))
                {
                    oS.utilDecodeResponse();
                    oS.SaveResponseBody(Path.Combine(Path.GetDirectoryName(Application.ExecutablePath), "DaXCaps", oS.oFlags["dax_id"] + "_DaX_" + oS.RequestHeaders["Range"].Substring("bytes=".Length) + "_XaD_" + oS.SuggestedFilename));
                }
            };

            FiddlerApplication.AfterSessionComplete += (oS) =>
            {
                Console.WriteLine("Finished session:\t" + oS.fullUrl);
            };

            #endregion AttachEventListeners



            string sSAZInfo = "NoSAZ";
            Console.WriteLine(String.Format("Starting {0} ({1})...", FiddlerApplication.GetVersionString(), sSAZInfo));

            CONFIG.IgnoreServerCertErrors = false;
            FiddlerApplication.Prefs.SetBoolPref("fiddler.network.streaming.abortifclientaborts", true);

            FiddlerCoreStartupFlags oFCSF = FiddlerCoreStartupFlags.Default;
            int iPort = 7777;
            oFCSF = FiddlerCoreStartupFlags.Default & ~FiddlerCoreStartupFlags.RegisterAsSystemProxy;
            FiddlerApplication.Startup(iPort, oFCSF);

            FiddlerApplication.Log.LogFormat("Created endpoint listening on port {0}", iPort);

            FiddlerApplication.Log.LogFormat("Starting with settings: [{0}]", oFCSF);
            FiddlerApplication.Log.LogFormat("Gateway: {0}", CONFIG.UpstreamGateway.ToString());

            oSecureEndpoint = FiddlerApplication.CreateProxyEndpoint(iSecureEndpointPort, true, sSecureEndpointHostname);
            if (null != oSecureEndpoint)
            {
                FiddlerApplication.Log.LogFormat("Created secure endpoint listening on port {0}, using a HTTPS certificate for '{1}'", iSecureEndpointPort, sSecureEndpointHostname);
            }
        }