From 70d5821f6f8b66f613891fa788da9dac9dee7088 Mon Sep 17 00:00:00 2001 From: Bryce Kwon Date: Thu, 16 Jul 2026 08:57:12 -1000 Subject: Clamp the log offset to bound history walks A crafted `ofs` could send cgit walking most of the history for one request. --- source/cgit.c | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) (limited to 'source/cgit.c') diff --git a/source/cgit.c b/source/cgit.c index d80aebd..156d2a7 100644 --- a/source/cgit.c +++ b/source/cgit.c @@ -344,7 +344,17 @@ static void querystring_cb(const char *name, const char *value) ctx.qry.oid2 = xstrdup(value); ctx.qry.has_oid = 1; } else if (!strcmp(name, "ofs")) { - ctx.qry.ofs = atoi(value); + /* Bound the upper end so a crafted value cannot force a walk + * over the whole history (and strtol avoids the atoi overflow). + * Only clamp the upper end: ofs is overloaded, the stats page + * submits -1 for "all authors", and the log skip loop already + * floors negatives at zero. */ + long ofs = strtol(value, NULL, 10); + if (ofs > 100000) + ofs = 100000; + else if (ofs < -1) + ofs = -1; + ctx.qry.ofs = ofs; } else if (!strcmp(name, "path")) { ctx.qry.path = trim_end(value, '/'); } else if (!strcmp(name, "name")) { -- cgit v2.8.0