Skip to content

Commit b935dc8

Browse files
committed
simplify codebase by using one thread/conn, instead of preforked procs
the existing codebase used an elaborate and complex approach for its parallelism: 5 different config file options, namely - MaxClients - MinSpareServers - MaxSpareServers - StartServers - MaxRequestsPerChild were used to steer how (and how many) parallel processes tinyproxy would spin up at start, how many processes at each point needed to be idle, etc. it seems all preforked processes would listen on the server port and compete with each other about who would get assigned the new incoming connections. since some data needs to be shared across those processes, a half- baked "shared memory" implementation was provided for this purpose. that implementation used to use files in the filesystem, and since it had a big FIXME comment, the author was well aware of how hackish that approach was. this entire complexity is now removed. the main thread enters a loop which polls on the listening fds, then spins up a new thread per connection, until the maximum number of connections (MaxClients) is hit. this is the only of the 5 config options left after this cleanup. since threads share the same address space, the code necessary for shared memory access has been removed. this means that the other 4 mentioned config option will now produce a parse error, when encountered. currently each thread uses a hardcoded default of 256KB per thread for the thread stack size, which is quite lavish and should be sufficient for even the worst C libraries, but people may want to tweak this value to the bare minimum, thus we may provide a new config option for this purpose in the future. i suspect that on heavily optimized C libraries such a musl, a stack size of 8-16 KB per thread could be sufficient. since the existing list implementation in vector.c did not provide a way to remove a single item from an existing list, i added my own list implementation from my libulz library which offers this functionality, rather than trying to add an ad-hoc, and perhaps buggy implementation to the vector_t list code. the sblist code is contained in an 80 line C file and as simple as it can get, while offering good performance and is proven bugfree due to years of use in other projects.
1 parent 3a7aa15 commit b935dc8

13 files changed

Lines changed: 316 additions & 559 deletions

File tree

docs/man5/tinyproxy.conf.txt.in

Lines changed: 1 addition & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -176,37 +176,11 @@ The possible keywords and their descriptions are as follows:
176176

177177
*MaxClients*::
178178

179-
Tinyproxy creates one child process for each connected client.
179+
Tinyproxy creates one thread for each connected client.
180180
This options specifies the absolute highest number processes that
181181
will be created. With other words, only MaxClients clients can be
182182
connected to Tinyproxy simultaneously.
183183

184-
*MinSpareServers*::
185-
*MaxSpareServers*::
186-
187-
Tinyproxy always keeps a certain number of idle child processes
188-
so that it can handle new incoming client requests quickly.
189-
`MinSpareServer` and `MaxSpareServers` control the lower and upper
190-
limits for the number of spare processes. I.e. when the number of
191-
spare servers drops below `MinSpareServers` then Tinyproxy will
192-
start forking new spare processes in the background and when the
193-
number of spare processes exceeds `MaxSpareServers` then Tinyproxy
194-
will kill off extra processes.
195-
196-
*StartServers*::
197-
198-
The number of servers to start initially. This should usually be
199-
set to a value between MinSpareServers and MaxSpareServers.
200-
201-
*MaxRequestsPerChild*::
202-
203-
This limits the number of connections that a child process
204-
will handle before it is killed. The default value is `0`
205-
which disables this feature. This option is meant as an
206-
emergency measure in the case of problems with memory leakage.
207-
In that case, setting `MaxRequestsPerChild` to a value of e.g.
208-
1000, or 10000 can be useful.
209-
210184
*Allow*::
211185
*Deny*::
212186

etc/tinyproxy.conf.in

Lines changed: 0 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -189,30 +189,6 @@ LogLevel Info
189189
#
190190
MaxClients 100
191191

192-
#
193-
# MinSpareServers/MaxSpareServers: These settings set the upper and
194-
# lower limit for the number of spare servers which should be available.
195-
#
196-
# If the number of spare servers falls below MinSpareServers then new
197-
# server processes will be spawned. If the number of servers exceeds
198-
# MaxSpareServers then the extras will be killed off.
199-
#
200-
MinSpareServers 5
201-
MaxSpareServers 20
202-
203-
#
204-
# StartServers: The number of servers to start initially.
205-
#
206-
StartServers 10
207-
208-
#
209-
# MaxRequestsPerChild: The number of connections a thread will handle
210-
# before it is killed. In practise this should be set to 0, which
211-
# disables thread reaping. If you do notice problems with memory
212-
# leakage, then set this to something like 10000.
213-
#
214-
MaxRequestsPerChild 0
215-
216192
#
217193
# Allow: Customization of authorization controls. If there are any
218194
# access control keywords then the default action is to DENY. Otherwise,

src/Makefile.am

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,10 +48,11 @@ tinyproxy_SOURCES = \
4848
upstream.c upstream.h \
4949
basicauth.c basicauth.h \
5050
base64.c base64.h \
51+
sblist.c sblist.h \
5152
connect-ports.c connect-ports.h
5253

5354
EXTRA_tinyproxy_SOURCES = filter.c filter.h \
5455
reverse-proxy.c reverse-proxy.h \
5556
transparent-proxy.c transparent-proxy.h
5657
tinyproxy_DEPENDENCIES = @ADDITIONAL_OBJECTS@
57-
tinyproxy_LDADD = @ADDITIONAL_OBJECTS@
58+
tinyproxy_LDADD = @ADDITIONAL_OBJECTS@ -lpthread

0 commit comments

Comments
 (0)