ReDoS in message formater using Slack notifications integration that can fully occupy Sidekiq utilization

Please read the process on how to fix security issues before starting to work on the issue. Vulnerabilities must be fixed in a security mirror.

HackerOne report #2428902 by joaxcar on 2024-03-21, assigned to @cmaxim:

Report | Attachments | How To Reproduce

Report

Summary

Hi team! I think this is my last ReDoS issue :) when I first found this one, I did not understand the impact, but after learning more about Sidekiq, I now see that this one also has the potential for high availability impact.

An attacker can configure Slack notifications as an integration. This is done by providing an incoming webhook to a Slack app. When a new issue is created, a message will be sent to the Slack app, and it will be posted in the designated Slack channel.

When GitLab is preparing the issue description to be sent to Slack this code will run

RELATIVE_LINK_REGEX = %r{!\[[^\]]*\]\((/uploads/[^\)]*)\)}  
...  
def format_relative_links(string)  
        string.gsub(RELATIVE_LINK_REGEX, "#{project_url}\\1")  
end  

Which tries to extract markdown image links ![](). This RELATIVE_LINK_REGEX is subject to polynomial complexity when evaluated against a long string of this format

"![".repeat(500000)  

If an attacker sets up an integration like this and starts creating issues with this string as described, this regexp will run inside the Sidekiq process. These jobs in Sidekiq do not look like having any timeout and will run for a very long time. By default, Sidekiq has 20 threads to run jobs with. By creating a minimum of 20 issues in the project, the attacker will thus block Sidekiq from processing other background jobs for the server (such as sending emails, creating pipelines, and exporting/importing projects etc).

Steps to reproduce

Test this on a self hosted server

  1. Log in as the attacker
  2. Create a new project
  3. Go to https://gitlab.example.com/GROUP/PROJECT/-/settings/integrations/slack/edit
  4. Fill out the form and leave all checkboxes checked. And write any URL in the webhook bar. I don't think you need to create a really webhook; the attack seems to work anyway.
  5. Now go to https://gitlab.com/GROUP/PROJECT/-/issues/new give it a name
  6. Open devtools and run this`
"![".repeat(500000)  

Click the small "copy" icon to copy the output
7. Put the long string in the description and click create (make sure to keep the network tab of devtools open)
8. When the request is done, filter for issues in the network tab of dev tools, find the post request, and right-click it. Open "copy" and click "copy as fetch"
9. in the console of devtools run the copied command 20+ times

  1. Log in as an admin user to the gitlab instance.
  2. Go to https://gitlab.com/GROUP/PROJECT/admin/background_jobs and you should see something like this

blocked1.png

blocked2.png

The 20 Blocking jobs should be your Integration jobs. The request queue should eventually just grow as the jobs are blocking all 20 threads.

Impact

ReDoS issue allows to block all threads in Sidekiq which will block all other background jobs to run

What is the current bug behavior?

The RELATIVE_LINK_REGEX regexp is subject to polynomial runtime

What is the expected correct behavior?

The regexp should be restricted in size or have other limits

Output of checks

Results of GitLab environment info
System information  
System:		Debian 12  
Proxy:		no  
Current User:	git  
Using RVM:	no  
Ruby Version:	3.1.4p223  
Gem Version:	3.5.5  
Bundler Version:2.5.5  
Rake Version:	13.0.6  
Redis Version:	7.0.15  
Sidekiq Version:7.1.6  
Go Version:	unknown

GitLab information  
Version:	16.9.2-ee  
Revision:	0d71d32d321  
Directory:	/opt/gitlab/embedded/service/gitlab-rails  
DB Adapter:	PostgreSQL  
DB Version:	14.10  
Elasticsearch:	no  
Geo:		no  
Using LDAP:	no  
Using Omniauth:	yes  
Omniauth Providers:

GitLab Shell  
Version:	14.33.0  
Repository storages:  
- default: 	unix:/var/opt/gitlab/gitaly/gitaly.socket  
GitLab Shell path:		/opt/gitlab/embedded/service/gitlab-shell

Gitaly  
- default Address: 	unix:/var/opt/gitlab/gitaly/gitaly.socket  
- default Version: 	16.9.2  
- default Git Version: 	2.43.0  

Impact

ReDoS issue allows to block all threads in Sidekiq which will block all other background jobs to run

Attachments

Warning: Attachments received through HackerOne, please exercise caution!

How To Reproduce

Please add reproducibility information to this section: