From 80912b7d438a4fba707f5fa8dc14c304ad8e603a Mon Sep 17 00:00:00 2001 From: Cody Kickertz Date: Sun, 21 Dec 2025 12:21:31 -0600 Subject: [PATCH] fix(security): prevent path traversal and command injection (#102) Co-authored-by: admin --- src/NzbDrone.Common/ServiceProvider.cs | 6 +++--- src/Radarr.Http/Frontend/Mappers/BackupFileMapper.cs | 12 +++++++++++- 2 files changed, 14 insertions(+), 4 deletions(-) diff --git a/src/NzbDrone.Common/ServiceProvider.cs b/src/NzbDrone.Common/ServiceProvider.cs index 5914bde497..513f2f67bc 100644 --- a/src/NzbDrone.Common/ServiceProvider.cs +++ b/src/NzbDrone.Common/ServiceProvider.cs @@ -184,9 +184,9 @@ public void Start(string serviceName) public void Restart(string serviceName) { - var args = string.Format("/C net.exe stop \"{0}\" && net.exe start \"{0}\"", serviceName); - - _processProvider.Start("cmd.exe", args); + _logger.Info("Restarting {0} Service...", serviceName); + Stop(serviceName); + Start(serviceName); } public void SetPermissions(string serviceName) diff --git a/src/Radarr.Http/Frontend/Mappers/BackupFileMapper.cs b/src/Radarr.Http/Frontend/Mappers/BackupFileMapper.cs index adc08c319f..df765019e0 100644 --- a/src/Radarr.Http/Frontend/Mappers/BackupFileMapper.cs +++ b/src/Radarr.Http/Frontend/Mappers/BackupFileMapper.cs @@ -19,7 +19,17 @@ public override string Map(string resourceUrl) { var path = resourceUrl.Replace("/backup/", "").Replace('/', Path.DirectorySeparatorChar); - return Path.Combine(_backupService.GetBackupFolder(), path); + var basePath = Path.GetFullPath(_backupService.GetBackupFolder()); + var filePath = Path.GetFullPath(Path.Combine(basePath, path)); + + // Prevent path traversal - ensure path stays within backup folder + if (!filePath.StartsWith(basePath + Path.DirectorySeparatorChar) && + !filePath.Equals(basePath, System.StringComparison.Ordinal)) + { + return null; + } + + return filePath; } public override bool CanHandle(string resourceUrl)