Safe TH1 docs
(1) By Warren Young (wyetr) on 2020-09-09 21:03:17 [source]
I came across a claim in the docs that enabling the
--with-th1-docs build-time configuration option is a security risk. That struck me as dubious since TH1's scope is so constrained, on purpose.
I dug into it, and it looks like the two main risks are:
Various sorts of DoS: infinite loops, causing Fossil to chew through arbitrary amounts of CPU rendering huge Markdown strings, etc.
It seems to me that there are straightforward mitigations for this:
- Install a watchdog timer on the script exec call and abort that execution if it takes too long. This invites an arms race where an attacker just re-execs the code that runs out the timers chewing up CPU resources, but there are tools for coping with that, such as fail2ban.
- Select a server method that allows parallel connections, so that one jammed-up conn child doesn't prevent others from being handled at the same time.
- Apply system limits to the child processes. Many server methods have direct support for this (e.g., in systemd) and for those that don't, there's ulimit on all POSIX systems, and presumably something similar on Windows.
Much more serious, the
querycommand. I assume that allows arbitrary SQL; if so, it allows arbitrary repo damage. Therefore, I suggest that Fossil offer a mode where it installs an authorizer allowing only
SELECTon all TH1 paths that accept data from non-Admin or Setup users, including embedded docs.
Given sufficient internal protections on this mechanism, we might be able to enable it by default.
(2) By Stephan Beal (stephan) on 2020-09-09 21:31:45 in reply to 1 [link] [source]
This invites an arms race where an attacker just re-execs the code that runs out the timers chewing up CPU resources
Hitting the timeline with a very large "n" or the
/stat page on a large repo can also be used to chew on the CPU. An infinite loop, OTOH, could easily be accidentally introduced while composing a page.
One absolutely silly, but maybe realistic, option is to simply limit the number of iterations on th1 loops to some arbitrary number, e.g., 1k. Are there valid uses (in fossil) for arbitrarily long loops? Perhaps a separate th1 command could remove or increase that limit.
Much more serious, the query command. I assume that allows arbitrary SQL; if so, it allows arbitrary repo damage.
That one uses an authorizer installed by
which allows restricted read access and no write access:
An infinite recursive query could also hypothetically kill the page but the authorizer also limits the VDBE opcodes to 10k, so it would break off at some point:
(3) By Warren Young (wyetr) on 2020-09-09 21:57:47 in reply to 2 [link] [source]
installed by repo_restrict_sql():
report_restrict_sql(), part of
report.c, which I found when grepping prior to composing the prior message, but I didn't think the it had anything to do with running TH1! That's part of the ticket mechanism.
(4) By Stephan Beal (stephan) on 2020-09-09 22:04:42 in reply to 3 [link] [source]
That's part of the ticket mechanism
That caught me by surprise as well, but the code doesn't lie! Presumably the security requirements of that command just happened to coincide with the already-existing ticket query authorizer.
(5) By Warren Young (wyetr) on 2020-09-09 22:13:33 in reply to 4 [link] [source]
That was a long way of saying, "Yes, I really did look at the code before posting!" :)