Problem/Motivation
This was originally reported as a private security issue but cleared by the security team for a public issue
Imagine there is a file with fid 999, uploaded to a Group. FID's are incremental, so one could easily guess this.
Now an attacker logs in, and is able to add files to content.
The code in core/modules/file/src/Element/ManagedFile.php allows to guess the file id and attach the specific file with the node.
Steps to reproduce
- Install Drupal with the Standard profile.
- Set up the private files (
$settings['file_private_path']insettings.php). -
Grant the permissions Create report content, View own unpublished content, and Administer node published status to the Content editor role.
Verify that it does not have the permission Bypass content access control. - Create two users with the Content editor role.
-
Create a content type named
reportwith a file field namedfield_attachment.- Configure the file field to use the private files upload destination.
- Set the cardinality to Unlimited.
-
As a user with the Content editor role:
- Create a node of type
report. - Upload a file named
test_1.txtto thefield_attachmentfield. - Mark the node as unpublished.
- Save the node.
- Create a node of type
-
As another user with the Content editor role:
- Visit the node creation form for the
reportcontent type. - Open the browser developer tools.
- Edit the
<input>element with the attributename="field_attachment[0][fids]". - Add the attribute
value="1"(increment the value and retry if the following steps do not reveal the issue). - Upload another file named
test_2.txtusing thefield_attachmentfield. - After the AJAX upload completes, the widget displays both
test_1.txtandtest_2.txt.
- Visit the node creation form for the
Proposed resolution
Add the validation in ManagedFile::valueCallback() element to check that user has download access of the file using $file->access('download').
Remaining tasks
Needs fix
User interface changes
N/A
Introduced terminology
N/A
API changes
N/A
Data model changes
N/A
Release notes snippet
N/A
| Comment | File | Size | Author |
|---|---|---|---|
| #17 | 3593472_17_regression.patch | 781 bytes | aporie |
Issue fork drupal-3593472
Show commands
Start within a Git clone of the project using the version control instructions.
Or, if you do not have SSH keys set up on git.drupalcode.org:
Comments
Comment #3
mohit_aghera commentedComment #4
mohit_aghera commentedComment #5
smustgrave commentedSmall comments/questions on the MR.
Comment #6
mohit_aghera commentedComment #7
smustgrave commentedThink feedback has been addressed here. The thread about expanding a test was a question and I also couldn't find a spot so lets see what committers think.
Comment #8
godotislateQ on the MR.
Comment #9
godotislateQuestion answered, thanks to @starlight-sparkle. Back to RTBC.
Comment #12
godotislateCommitted and pushed 80ff540 to main and d5bb973 to 11.x. Thanks!
This probably can go to 11.4.x as well, but will consult other committers.
Comment #14
godotislateConsulted with @longwave, and he agreed this is good for 11.4. Committed 83a5f2b and pushed to 11.4.x.
Comment #17
aporieThis security improvement introduces a regression in the following case:
Suggestion of improvement:
Only target
$file->isPermanent(). Assuming that when the form is submitted the file is set as permanent, this should allow the above scenario without opening wide access to previously uploaded ID guessing file.To further improve security, Drupal must be configured to erase temporary file as soon as possible (every 24h).
I'm attaching a patch which works for my case, in case it may help others.
Comment #18
priyankampatil commented@aporie I faced a similar issue with Webform submissions where, if a file field was marked as required, the form would not allow the submission to complete. However, even after applying the patch, the submission is still being blocked when the mandatory file field is present.