We are currently solving the following issue within our repository. Here is the issue text:
--- BEGIN ISSUE ---
ServerException instead of ProxyServerError
##### Steps to reproduce the problem:

```
>>> from libmproxy.proxy.server import ProxyServer
>>> from libmproxy.proxy.config import ProxyConfig
>>> ProxyServer(ProxyConfig(port=80))
(...)
ServerException: Error starting proxy server: error(13, 'Permission denied')
```
##### What is the expected behavior?

According to the documentation:

```
>>> ProxyServer?                       
Type:            type
String form:     <class 'libmproxy.proxy.server.ProxyServer'>
File:            /usr/lib/python2.7/dist-packages/libmproxy/proxy/server.py
Init definition: ProxyServer(self, config)
Docstring:       <no docstring>
Init docstring:  Raises ProxyServerError if there's a startup problem.
```

the expected behavior is 

```
>>> ProxyServer(ProxyConfig(port=80))
(...)
ProxyServerError: Error starting proxy server: error(13, 'Permission denied')
```
##### What went wrong?

Maybe the documentation is wrong?
##### Any other comments?

Nope.

---

Mitmproxy Version: 0.15-2
Operating System: Debian Sid.


--- END ISSUE ---

Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
--- BEGIN FILES ---
Path: `mitmproxy/proxy/server.py`
Content:
```
1 from __future__ import (absolute_import, print_function, division)
2 
3 import traceback
4 import sys
5 import socket
6 import six
7 
8 from netlib import tcp
9 from netlib.exceptions import TcpException
10 from netlib.http.http1 import assemble_response
11 from ..exceptions import ProtocolException, ServerException, ClientHandshakeException, Kill
12 from ..models import ClientConnection, make_error_response
13 from .modes import HttpUpstreamProxy, HttpProxy, ReverseProxy, TransparentProxy, Socks5Proxy
14 from .root_context import RootContext, Log
15 
16 
17 class DummyServer:
18     bound = False
19 
20     def __init__(self, config):
21         self.config = config
22 
23     def set_channel(self, channel):
24         pass
25 
26     def serve_forever(self):
27         pass
28 
29     def shutdown(self):
30         pass
31 
32 
33 class ProxyServer(tcp.TCPServer):
34     allow_reuse_address = True
35     bound = True
36 
37     def __init__(self, config):
38         """
39             Raises ProxyServerError if there's a startup problem.
40         """
41         self.config = config
42         try:
43             super(ProxyServer, self).__init__((config.host, config.port))
44         except socket.error as e:
45             six.reraise(
46                 ServerException,
47                 ServerException('Error starting proxy server: ' + repr(e)),
48                 sys.exc_info()[2]
49             )
50         self.channel = None
51 
52     def set_channel(self, channel):
53         self.channel = channel
54 
55     def handle_client_connection(self, conn, client_address):
56         h = ConnectionHandler(
57             conn,
58             client_address,
59             self.config,
60             self.channel
61         )
62         h.handle()
63 
64 
65 class ConnectionHandler(object):
66 
67     def __init__(self, client_conn, client_address, config, channel):
68         self.config = config
69         """@type: mitmproxy.proxy.config.ProxyConfig"""
70         self.client_conn = ClientConnection(
71             client_conn,
72             client_address,
73             None)
74         """@type: mitmproxy.proxy.connection.ClientConnection"""
75         self.channel = channel
76         """@type: mitmproxy.controller.Channel"""
77 
78     def _create_root_layer(self):
79         root_context = RootContext(
80             self.client_conn,
81             self.config,
82             self.channel
83         )
84 
85         mode = self.config.mode
86         if mode == "upstream":
87             return HttpUpstreamProxy(
88                 root_context,
89                 self.config.upstream_server.address
90             )
91         elif mode == "transparent":
92             return TransparentProxy(root_context)
93         elif mode == "reverse":
94             server_tls = self.config.upstream_server.scheme == "https"
95             return ReverseProxy(
96                 root_context,
97                 self.config.upstream_server.address,
98                 server_tls
99             )
100         elif mode == "socks5":
101             return Socks5Proxy(root_context)
102         elif mode == "regular":
103             return HttpProxy(root_context)
104         elif callable(mode):  # pragma: no cover
105             return mode(root_context)
106         else:  # pragma: no cover
107             raise ValueError("Unknown proxy mode: %s" % mode)
108 
109     def handle(self):
110         self.log("clientconnect", "info")
111 
112         root_layer = self._create_root_layer()
113 
114         try:
115             root_layer = self.channel.ask("clientconnect", root_layer)
116             root_layer()
117         except Kill:
118             self.log("Connection killed", "info")
119         except ProtocolException as e:
120 
121             if isinstance(e, ClientHandshakeException):
122                 self.log(
123                     "Client Handshake failed. "
124                     "The client may not trust the proxy's certificate for {}.".format(e.server),
125                     "error"
126                 )
127                 self.log(repr(e), "debug")
128             else:
129                 self.log(repr(e), "info")
130 
131                 self.log(traceback.format_exc(), "debug")
132             # If an error propagates to the topmost level,
133             # we send an HTTP error response, which is both
134             # understandable by HTTP clients and humans.
135             try:
136                 error_response = make_error_response(502, repr(e))
137                 self.client_conn.send(assemble_response(error_response))
138             except TcpException:
139                 pass
140         except Exception:
141             self.log(traceback.format_exc(), "error")
142             print(traceback.format_exc(), file=sys.stderr)
143             print("mitmproxy has crashed!", file=sys.stderr)
144             print("Please lodge a bug report at: https://github.com/mitmproxy/mitmproxy", file=sys.stderr)
145 
146         self.log("clientdisconnect", "info")
147         self.channel.tell("clientdisconnect", root_layer)
148         self.client_conn.finish()
149 
150     def log(self, msg, level):
151         msg = "{}: {}".format(repr(self.client_conn.address), msg)
152         self.channel.tell("log", Log(msg, level))
153
```
--- END FILES ---

Please first localize the bug based on the issue statement, and then generate a patch according to the `git diff` format fenced by three backticks.

Here is an example:

```diff
diff --git a/examples/server_async.py b/examples/server_async.py
--- a/examples/server_async.py
+++ b/examples/server_async.py
@@ -313,4 +313,4 @@
 
 
 if __name__ == "__main__":
-    asyncio.run(run_async_server("."), debug=True)
+    asyncio.run(run_async_server(), debug=True)
diff --git a/examples/server_sync.py b/examples/server_sync.py
--- a/examples/server_sync.py
+++ b/examples/server_sync.py
@@ -313,5 +313,5 @@
 
 
 if __name__ == "__main__":
-    server = run_sync_server(".")
+    server = run_sync_server()
     server.shutdown()

```

diff --git a/mitmproxy/proxy/server.py b/mitmproxy/proxy/server.py
--- a/mitmproxy/proxy/server.py
+++ b/mitmproxy/proxy/server.py
@@ -36,7 +36,7 @@
 
     def __init__(self, config):
         """
-            Raises ProxyServerError if there's a startup problem.
+            Raises ServerException if there's a startup problem.
         """
         self.config = config
         try:

{"golden_diff": "diff --git a/mitmproxy/proxy/server.py b/mitmproxy/proxy/server.py\n--- a/mitmproxy/proxy/server.py\n+++ b/mitmproxy/proxy/server.py\n@@ -36,7 +36,7 @@\n \n     def __init__(self, config):\n         \"\"\"\n-            Raises ProxyServerError if there's a startup problem.\n+            Raises ServerException if there's a startup problem.\n         \"\"\"\n         self.config = config\n         try:\n", "issue": "ServerException instead of ProxyServerError\n##### Steps to reproduce the problem:\n\n```\n>>> from libmproxy.proxy.server import ProxyServer\n>>> from libmproxy.proxy.config import ProxyConfig\n>>> ProxyServer(ProxyConfig(port=80))\n(...)\nServerException: Error starting proxy server: error(13, 'Permission denied')\n```\n##### What is the expected behavior?\n\nAccording to the documentation:\n\n```\n>>> ProxyServer?                       \nType:            type\nString form:     <class 'libmproxy.proxy.server.ProxyServer'>\nFile:            /usr/lib/python2.7/dist-packages/libmproxy/proxy/server.py\nInit definition: ProxyServer(self, config)\nDocstring:       <no docstring>\nInit docstring:  Raises ProxyServerError if there's a startup problem.\n```\n\nthe expected behavior is \n\n```\n>>> ProxyServer(ProxyConfig(port=80))\n(...)\nProxyServerError: Error starting proxy server: error(13, 'Permission denied')\n```\n##### What went wrong?\n\nMaybe the documentation is wrong?\n##### Any other comments?\n\nNope.\n\n---\n\nMitmproxy Version: 0.15-2\nOperating System: Debian Sid.\n\n", "before_files": [{"content": "from __future__ import (absolute_import, print_function, division)\n\nimport traceback\nimport sys\nimport socket\nimport six\n\nfrom netlib import tcp\nfrom netlib.exceptions import TcpException\nfrom netlib.http.http1 import assemble_response\nfrom ..exceptions import ProtocolException, ServerException, ClientHandshakeException, Kill\nfrom ..models import ClientConnection, make_error_response\nfrom .modes import HttpUpstreamProxy, HttpProxy, ReverseProxy, TransparentProxy, Socks5Proxy\nfrom .root_context import RootContext, Log\n\n\nclass DummyServer:\n    bound = False\n\n    def __init__(self, config):\n        self.config = config\n\n    def set_channel(self, channel):\n        pass\n\n    def serve_forever(self):\n        pass\n\n    def shutdown(self):\n        pass\n\n\nclass ProxyServer(tcp.TCPServer):\n    allow_reuse_address = True\n    bound = True\n\n    def __init__(self, config):\n        \"\"\"\n            Raises ProxyServerError if there's a startup problem.\n        \"\"\"\n        self.config = config\n        try:\n            super(ProxyServer, self).__init__((config.host, config.port))\n        except socket.error as e:\n            six.reraise(\n                ServerException,\n                ServerException('Error starting proxy server: ' + repr(e)),\n                sys.exc_info()[2]\n            )\n        self.channel = None\n\n    def set_channel(self, channel):\n        self.channel = channel\n\n    def handle_client_connection(self, conn, client_address):\n        h = ConnectionHandler(\n            conn,\n            client_address,\n            self.config,\n            self.channel\n        )\n        h.handle()\n\n\nclass ConnectionHandler(object):\n\n    def __init__(self, client_conn, client_address, config, channel):\n        self.config = config\n        \"\"\"@type: mitmproxy.proxy.config.ProxyConfig\"\"\"\n        self.client_conn = ClientConnection(\n            client_conn,\n            client_address,\n            None)\n        \"\"\"@type: mitmproxy.proxy.connection.ClientConnection\"\"\"\n        self.channel = channel\n        \"\"\"@type: mitmproxy.controller.Channel\"\"\"\n\n    def _create_root_layer(self):\n        root_context = RootContext(\n            self.client_conn,\n            self.config,\n            self.channel\n        )\n\n        mode = self.config.mode\n        if mode == \"upstream\":\n            return HttpUpstreamProxy(\n                root_context,\n                self.config.upstream_server.address\n            )\n        elif mode == \"transparent\":\n            return TransparentProxy(root_context)\n        elif mode == \"reverse\":\n            server_tls = self.config.upstream_server.scheme == \"https\"\n            return ReverseProxy(\n                root_context,\n                self.config.upstream_server.address,\n                server_tls\n            )\n        elif mode == \"socks5\":\n            return Socks5Proxy(root_context)\n        elif mode == \"regular\":\n            return HttpProxy(root_context)\n        elif callable(mode):  # pragma: no cover\n            return mode(root_context)\n        else:  # pragma: no cover\n            raise ValueError(\"Unknown proxy mode: %s\" % mode)\n\n    def handle(self):\n        self.log(\"clientconnect\", \"info\")\n\n        root_layer = self._create_root_layer()\n\n        try:\n            root_layer = self.channel.ask(\"clientconnect\", root_layer)\n            root_layer()\n        except Kill:\n            self.log(\"Connection killed\", \"info\")\n        except ProtocolException as e:\n\n            if isinstance(e, ClientHandshakeException):\n                self.log(\n                    \"Client Handshake failed. \"\n                    \"The client may not trust the proxy's certificate for {}.\".format(e.server),\n                    \"error\"\n                )\n                self.log(repr(e), \"debug\")\n            else:\n                self.log(repr(e), \"info\")\n\n                self.log(traceback.format_exc(), \"debug\")\n            # If an error propagates to the topmost level,\n            # we send an HTTP error response, which is both\n            # understandable by HTTP clients and humans.\n            try:\n                error_response = make_error_response(502, repr(e))\n                self.client_conn.send(assemble_response(error_response))\n            except TcpException:\n                pass\n        except Exception:\n            self.log(traceback.format_exc(), \"error\")\n            print(traceback.format_exc(), file=sys.stderr)\n            print(\"mitmproxy has crashed!\", file=sys.stderr)\n            print(\"Please lodge a bug report at: https://github.com/mitmproxy/mitmproxy\", file=sys.stderr)\n\n        self.log(\"clientdisconnect\", \"info\")\n        self.channel.tell(\"clientdisconnect\", root_layer)\n        self.client_conn.finish()\n\n    def log(self, msg, level):\n        msg = \"{}: {}\".format(repr(self.client_conn.address), msg)\n        self.channel.tell(\"log\", Log(msg, level))\n", "path": "mitmproxy/proxy/server.py"}], "after_files": [{"content": "from __future__ import (absolute_import, print_function, division)\n\nimport traceback\nimport sys\nimport socket\nimport six\n\nfrom netlib import tcp\nfrom netlib.exceptions import TcpException\nfrom netlib.http.http1 import assemble_response\nfrom ..exceptions import ProtocolException, ServerException, ClientHandshakeException, Kill\nfrom ..models import ClientConnection, make_error_response\nfrom .modes import HttpUpstreamProxy, HttpProxy, ReverseProxy, TransparentProxy, Socks5Proxy\nfrom .root_context import RootContext, Log\n\n\nclass DummyServer:\n    bound = False\n\n    def __init__(self, config):\n        self.config = config\n\n    def set_channel(self, channel):\n        pass\n\n    def serve_forever(self):\n        pass\n\n    def shutdown(self):\n        pass\n\n\nclass ProxyServer(tcp.TCPServer):\n    allow_reuse_address = True\n    bound = True\n\n    def __init__(self, config):\n        \"\"\"\n            Raises ServerException if there's a startup problem.\n        \"\"\"\n        self.config = config\n        try:\n            super(ProxyServer, self).__init__((config.host, config.port))\n        except socket.error as e:\n            six.reraise(\n                ServerException,\n                ServerException('Error starting proxy server: ' + repr(e)),\n                sys.exc_info()[2]\n            )\n        self.channel = None\n\n    def set_channel(self, channel):\n        self.channel = channel\n\n    def handle_client_connection(self, conn, client_address):\n        h = ConnectionHandler(\n            conn,\n            client_address,\n            self.config,\n            self.channel\n        )\n        h.handle()\n\n\nclass ConnectionHandler(object):\n\n    def __init__(self, client_conn, client_address, config, channel):\n        self.config = config\n        \"\"\"@type: mitmproxy.proxy.config.ProxyConfig\"\"\"\n        self.client_conn = ClientConnection(\n            client_conn,\n            client_address,\n            None)\n        \"\"\"@type: mitmproxy.proxy.connection.ClientConnection\"\"\"\n        self.channel = channel\n        \"\"\"@type: mitmproxy.controller.Channel\"\"\"\n\n    def _create_root_layer(self):\n        root_context = RootContext(\n            self.client_conn,\n            self.config,\n            self.channel\n        )\n\n        mode = self.config.mode\n        if mode == \"upstream\":\n            return HttpUpstreamProxy(\n                root_context,\n                self.config.upstream_server.address\n            )\n        elif mode == \"transparent\":\n            return TransparentProxy(root_context)\n        elif mode == \"reverse\":\n            server_tls = self.config.upstream_server.scheme == \"https\"\n            return ReverseProxy(\n                root_context,\n                self.config.upstream_server.address,\n                server_tls\n            )\n        elif mode == \"socks5\":\n            return Socks5Proxy(root_context)\n        elif mode == \"regular\":\n            return HttpProxy(root_context)\n        elif callable(mode):  # pragma: no cover\n            return mode(root_context)\n        else:  # pragma: no cover\n            raise ValueError(\"Unknown proxy mode: %s\" % mode)\n\n    def handle(self):\n        self.log(\"clientconnect\", \"info\")\n\n        root_layer = self._create_root_layer()\n\n        try:\n            root_layer = self.channel.ask(\"clientconnect\", root_layer)\n            root_layer()\n        except Kill:\n            self.log(\"Connection killed\", \"info\")\n        except ProtocolException as e:\n\n            if isinstance(e, ClientHandshakeException):\n                self.log(\n                    \"Client Handshake failed. \"\n                    \"The client may not trust the proxy's certificate for {}.\".format(e.server),\n                    \"error\"\n                )\n                self.log(repr(e), \"debug\")\n            else:\n                self.log(repr(e), \"info\")\n\n                self.log(traceback.format_exc(), \"debug\")\n            # If an error propagates to the topmost level,\n            # we send an HTTP error response, which is both\n            # understandable by HTTP clients and humans.\n            try:\n                error_response = make_error_response(502, repr(e))\n                self.client_conn.send(assemble_response(error_response))\n            except TcpException:\n                pass\n        except Exception:\n            self.log(traceback.format_exc(), \"error\")\n            print(traceback.format_exc(), file=sys.stderr)\n            print(\"mitmproxy has crashed!\", file=sys.stderr)\n            print(\"Please lodge a bug report at: https://github.com/mitmproxy/mitmproxy\", file=sys.stderr)\n\n        self.log(\"clientdisconnect\", \"info\")\n        self.channel.tell(\"clientdisconnect\", root_layer)\n        self.client_conn.finish()\n\n    def log(self, msg, level):\n        msg = \"{}: {}\".format(repr(self.client_conn.address), msg)\n        self.channel.tell(\"log\", Log(msg, level))\n", "path": "mitmproxy/proxy/server.py"}]}