SPEC and README: owner rulings, issues 2 to 5, internet-ready defaults #9
@@ -538,9 +538,9 @@ The settings, by group:
|
|||||||
- `WAF_PARANOIA_LEVEL` (default `1`), `WAF_ANOMALY_THRESHOLD` (default `5`):
|
- `WAF_PARANOIA_LEVEL` (default `1`), `WAF_ANOMALY_THRESHOLD` (default `5`):
|
||||||
the Core Rule Set's own two tuning values, at the Core Rule Set's own
|
the Core Rule Set's own two tuning values, at the Core Rule Set's own
|
||||||
defaults.
|
defaults.
|
||||||
- The sidecar also changes the Core Rule Set 4.25.0 in five ways that no
|
- The sidecar also changes the Core Rule Set 4.25.0 in five ways, since in
|
||||||
setting undoes, since in front of gitea each would otherwise refuse
|
front of gitea it would otherwise refuse ordinary requests. The changes
|
||||||
ordinary requests:
|
hold in front of every app, and no setting undoes them:
|
||||||
- PUT, PATCH and DELETE are allowed methods besides GET, HEAD, POST and
|
- PUT, PATCH and DELETE are allowed methods besides GET, HEAD, POST and
|
||||||
OPTIONS; APIs, container image pushes and package uploads use them.
|
OPTIONS; APIs, container image pushes and package uploads use them.
|
||||||
Other methods stay refused.
|
Other methods stay refused.
|
||||||
@@ -566,11 +566,18 @@ The settings, by group:
|
|||||||
such as `.gitignore`, `package.json`, `docker-compose.yml`,
|
such as `.gitignore`, `package.json`, `docker-compose.yml`,
|
||||||
`bin/docker-entrypoint` or a branch named `docker-build`, and gitea
|
`bin/docker-entrypoint` or a branch named `docker-build`, and gitea
|
||||||
reads these values as names within a repository or its own records, or
|
reads these values as names within a repository or its own records, or
|
||||||
as a page of its own site. What only these three rules refuse, such as
|
as a page of its own site. Like the other changes, this one holds in
|
||||||
`/etc/passwd` or `whoami` on its own, is therefore let through in
|
front of every app, not only gitea, and no setting restores the three
|
||||||
those parameters; path traversal (`../`), SQL and script injection and
|
rules in those parameters. What only these three rules refuse is let
|
||||||
PHP, Java and Node.js code are still refused there, and every other
|
through there, and that is more than a name such as `/etc/passwd` or
|
||||||
parameter and cookie keeps all three rules.
|
`whoami` on its own: commands such as `|cat /etc/passwd`,
|
||||||
|
`wget http://…` and `nc -e /bin/sh …`, and `file:///etc/passwd`, pass
|
||||||
|
as well. Path traversal (`../`), SQL and script injection and PHP,
|
||||||
|
Java and Node.js code are still refused there, and every other
|
||||||
|
parameter and cookie keeps all three rules. An app that uses one of
|
||||||
|
these parameters as a file on the server, or passes it to a shell,
|
||||||
|
gets no help from the three rules there (see "Risks the design has to
|
||||||
|
handle").
|
||||||
- Responses are not inspected. A raw file from a repository, such as a
|
- Responses are not inspected. A raw file from a repository, such as a
|
||||||
shell script, looks to the response rules like source code leaking
|
shell script, looks to the response rules like source code leaking
|
||||||
from the server.
|
from the server.
|
||||||
@@ -1136,36 +1143,59 @@ networks:
|
|||||||
`UPSTREAM_REQUEST_TIMEOUT` raised to fit. The Core Rule Set does not read
|
`UPSTREAM_REQUEST_TIMEOUT` raised to fit. The Core Rule Set does not read
|
||||||
an upload's body, which streams through without being held in memory.
|
an upload's body, which streams through without being held in memory.
|
||||||
- At the defaults (see "Configuration surface", attack detection), the Core
|
- At the defaults (see "Configuration surface", attack detection), the Core
|
||||||
Rule Set lets gitea's ordinary use through, whatever its files and
|
Rule Set lets gitea's ordinary use through, apart from the refusals in the
|
||||||
branches are called: browsing and views of files in a repository, with
|
next note: browsing and views of files in a repository, with their
|
||||||
their history, blame and the file tree; diffs, including their hidden
|
history, blame and the file tree; diffs, including their hidden lines and
|
||||||
lines and large files, and pull request review; git's clone, fetch and
|
large files, and pull request review; git's clone, fetch and push over
|
||||||
push over HTTP; signing in, including the return to the page a visitor
|
HTTP; signing in, including the return to the page a visitor came from and
|
||||||
came from and sign-in with Git Credential Manager, git-credential-oauth or
|
sign-in with Git Credential Manager, git-credential-oauth or tea; the
|
||||||
tea; the API's calls for a file and its commits; pushing and pulling
|
API's calls for a file and its commits; pushing and pulling container
|
||||||
container images and packages; Actions runners, and artifacts uploaded
|
images and packages; Actions runners, and artifacts uploaded with
|
||||||
with `actions/upload-artifact@v4`; and posting issues, pull requests,
|
`actions/upload-artifact@v4`; and posting issues, pull requests, comments,
|
||||||
comments, wiki pages and files saved in the web editor, code included,
|
wiki pages and files saved in the web editor, code included, since no body
|
||||||
since no body is read. It can still refuse a query string that reads to it
|
is read.
|
||||||
as an attack, most often a search: one for a name on its lists of system
|
- The Core Rule Set can still refuse the requests below. Each refusal
|
||||||
files and commands, such as `package.json`, `.gitignore` or
|
answers only that request, with 403, and bans no one by itself: it counts
|
||||||
`docker-compose.yml`, or for text that starts with a command name, such as
|
toward the error burst, which a person does not reach this way. The
|
||||||
`python3` or `ssh key`; or one holding a shell command with its options or
|
request log names the rule in `waf_rule_ids`, which `WAF_DISABLED_RULES`
|
||||||
a system path (`ls -la`, `sed -i`, `/bin/sh`), a command in backticks,
|
can switch off.
|
||||||
script code (`fetch(`, `${VAR}`, `process.env`), HTML (`<img src=`), an
|
- A query string that reads to it as an attack, most often a search: one
|
||||||
SQL statement (`SELECT * FROM users WHERE`), or a URL naming an IP address
|
for a name on its lists of system files and commands, such as
|
||||||
or `localhost`. The lists refuse such a name in any other query parameter
|
`package.json`, `.gitignore` or `docker-compose.yml`, or for text that
|
||||||
too, such as a release attachment uploaded through the API as
|
starts with a command name, such as `python3` or `ssh key`; or one
|
||||||
`docker-compose.yml`. A path can be refused as well: a file name ending in
|
holding a shell command with its options or a system path (`ls -la`,
|
||||||
`~`, or an `.xhtml` file whose path holds a space. Such a refusal answers
|
`sed -i`, `/bin/sh`), a command in backticks, script code (`fetch(`,
|
||||||
only that request, with 403, and bans no one by itself: it counts toward
|
`${VAR}`, `process.env`), HTML (`<img src=`), an SQL statement
|
||||||
the error burst, which a person searching does not reach. The request log
|
(`SELECT * FROM users WHERE`), or a URL naming an IP address or
|
||||||
names the rule in `waf_rule_ids`, which `WAF_DISABLED_RULES` can switch
|
`localhost`. The lists refuse such a name in any other query parameter
|
||||||
off.
|
too, such as a release attachment uploaded through the API as
|
||||||
|
`docker-compose.yml`.
|
||||||
|
- A branch, tag or file name that starts with `docker-`, `python3`,
|
||||||
|
`ansible`, `base64`, `whoami` or another entry on the Core Rule Set's
|
||||||
|
list of commands (932260), where gitea's own pages send it in a query
|
||||||
|
parameter that 930120, 932160 and 932260 still check: `refSubUrl`, the
|
||||||
|
branch or tag of a directory listing, sent when the listing asks for
|
||||||
|
its entries' last commits in a second request, as it does whenever
|
||||||
|
gitea takes more than a second to work them out; `name`, when a branch
|
||||||
|
is deleted or restored on the branches page; `tag`, when a release is
|
||||||
|
started from a tag; `template`, the file of an issue template, when an
|
||||||
|
issue is opened from it; and `rule_name`, when a branch protection
|
||||||
|
rule is opened for editing in the repository's settings. For a branch
|
||||||
|
named `docker-build`, a directory listing that makes that second
|
||||||
|
request leaves those last commits out and shows an error, and the
|
||||||
|
branches page shows an error instead of deleting or restoring the
|
||||||
|
branch. A release started from such a tag, an issue from such a
|
||||||
|
template or such a rule opened for editing gets the sidecar's 403
|
||||||
|
answer in place of its form.
|
||||||
|
- A path: a file name ending in `~`, or an `.xhtml` file whose path
|
||||||
|
holds a space.
|
||||||
- Artifact uploads from `actions/upload-artifact@v3` send the header
|
- Artifact uploads from `actions/upload-artifact@v3` send the header
|
||||||
`Content-Range`, which the Core Rule Set refuses (920450). Each file of
|
`Content-Range`, which the Core Rule Set refuses (920450). The action
|
||||||
the artifact is refused with 403 and the step fails; an artifact of more
|
sends two files at a time, does not retry a 403 and sends no further file
|
||||||
than 30 files also bans the runner through the error burst.
|
once one is refused, so an upload is refused once or twice, however many
|
||||||
|
files it holds, and the step fails. One upload does not ban the runner;
|
||||||
|
more than 30 such refusals from its address within a minute, as when many
|
||||||
|
jobs upload at once, ban it through the error burst.
|
||||||
`actions/upload-artifact@v4` does not send the header.
|
`actions/upload-artifact@v4` does not send the header.
|
||||||
- An Actions runner that reaches gitea through the sidecar sends requests
|
- An Actions runner that reaches gitea through the sidecar sends requests
|
||||||
all day. One older than version 0.4 (April 2026) asks for work every 2
|
all day. One older than version 0.4 (April 2026) asks for work every 2
|
||||||
@@ -1248,6 +1278,14 @@ networks:
|
|||||||
attack is still subject to the rule files, the limits and the bans, and
|
attack is still subject to the rule files, the limits and the bans, and
|
||||||
`WAF_BODY_LIMIT` switches body inspection on for apps whose forms carry no
|
`WAF_BODY_LIMIT` switches body inspection on for apps whose forms carry no
|
||||||
code.
|
code.
|
||||||
|
- An app that uses `path`, `ref` or another of the query parameters left out of
|
||||||
|
930120, 932160 and 932260 (see "Configuration surface", attack detection) as a
|
||||||
|
file on the server, or passes it to a shell: that change holds in front of
|
||||||
|
every app and no setting restores the three rules, so what only they refuse
|
||||||
|
reaches the app in those parameters, such as `/etc/passwd`, `|cat /etc/passwd`
|
||||||
|
or `nc -e /bin/sh …`. Path traversal (`../`) is still refused there. Such an
|
||||||
|
app has to check those values itself, or refuse what it must never receive in
|
||||||
|
them with a rule file.
|
||||||
- The admin endpoints can be reached from the internet: all but the health check
|
- The admin endpoints can be reached from the internet: all but the health check
|
||||||
need a token and are off while it is unset, and a missing or wrong token
|
need a token and are off while it is unset, and a missing or wrong token
|
||||||
counts toward the error burst, so a client guessing tokens is soon banned.
|
counts toward the error burst, so a client guessing tokens is soon banned.
|
||||||
|
|||||||
Reference in New Issue
Block a user