-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
3e2cc38
commit 1a60b26
Showing
9 changed files
with
338 additions
and
1 deletion.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1 +1,18 @@ | ||
# lblfixer_cve_2023_30839 | ||
# LabelGrup Networks, official PrestaShop Partner | ||
|
||
![LabelGrup Logo](logo.png) | ||
|
||
Module for PrestaShop <1.7.8.9 to fix CVE-2023-30839 vulnerability (SQL Injection) | ||
|
||
For further information, check the following links: | ||
- CVE: https://nvd.nist.gov/vuln/detail/CVE-2023-30839 | ||
- GitHub: https://github.com/PrestaShop/PrestaShop/security/advisories/GHSA-p379-cxqh-q822 | ||
|
||
**Instructions:** | ||
|
||
1. Download the latest release from this repository. | ||
2. Install the downloaded ZIP as a normal addon, this will replace/copy the needed files to your current PrestaShop. | ||
3. Be aware: If you remove the addon, your PrestaShop will be reverted to its original state, exposing the vulnerability again. | ||
|
||
Visit our website: | ||
https://www.labelgrup.com |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
Deny from all |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,22 @@ | ||
<?php | ||
/** | ||
* 2023 LabelGrup Networks SL | ||
* | ||
* NOTICE OF LICENSE | ||
* | ||
* READ ATTACHED LICENSE.TXT | ||
* | ||
* @author Manel Alonso <[email protected]>, <[email protected]> | ||
* @copyright 2023 LabelGrup Networks SL | ||
* @license LICENSE.TXT | ||
*/ | ||
|
||
header('Expires: Mon, 26 Jul 1997 05:00:00 GMT'); | ||
header('Last-Modified: '.gmdate('D, d M Y H:i:s').' GMT'); | ||
|
||
header('Cache-Control: no-store, no-cache, must-revalidate'); | ||
header('Cache-Control: post-check=0, pre-check=0', false); | ||
header('Pragma: no-cache'); | ||
|
||
header('Location: ../'); | ||
exit; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,22 @@ | ||
<?php | ||
/** | ||
* 2023 LabelGrup Networks SL | ||
* | ||
* NOTICE OF LICENSE | ||
* | ||
* READ ATTACHED LICENSE.TXT | ||
* | ||
* @author Manel Alonso <[email protected]>, <[email protected]> | ||
* @copyright 2023 LabelGrup Networks SL | ||
* @license LICENSE.TXT | ||
*/ | ||
|
||
header('Expires: Mon, 26 Jul 1997 05:00:00 GMT'); | ||
header('Last-Modified: '.gmdate('D, d M Y H:i:s').' GMT'); | ||
|
||
header('Cache-Control: no-store, no-cache, must-revalidate'); | ||
header('Cache-Control: post-check=0, pre-check=0', false); | ||
header('Pragma: no-cache'); | ||
|
||
header('Location: ../'); | ||
exit; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,238 @@ | ||
<?php | ||
|
||
/** | ||
* 2023 LabelGrup Networks SL | ||
* | ||
* NOTICE OF LICENSE | ||
* | ||
* READ ATTACHED LICENSE.TXT | ||
* | ||
* @author Manel Alonso <[email protected]>, <[email protected]> | ||
* @copyright 2023 LabelGrup Networks SL | ||
* @license LICENSE.TXT | ||
*/ | ||
|
||
if (!defined('_PS_VERSION_')) { | ||
exit; | ||
} | ||
|
||
class Lblfixer_cve_2023_30839 extends Module | ||
{ | ||
public function __construct() | ||
{ | ||
$this->name = 'lblfixer_cve_2023_30839'; | ||
$this->tab = 'front_office_features'; | ||
$this->version = '1.0.0'; | ||
$this->author = 'LabelGrup Networks SL, Manel Alonso'; | ||
$this->need_instance = 0; | ||
$this->displayName = $this->l('LabelGrup.com FIX CVE-2023-30839 (for PrestaShop <1.7.8.9)'); | ||
$this->description = $this->l('Fixes CVE-2023-30839 vulnerability.'); | ||
$this->ps_versions_compliancy = array('min' => '1.7.0', 'max' => '1.7.8.8'); | ||
$this->confirmUninstall = $this->l('Your shop will be vulnerable to CVE-2023-30839.') . | ||
$this->l('Are you sure you want to uninstall this addon?'); | ||
|
||
parent::__construct(); | ||
} | ||
|
||
public function install() | ||
{ | ||
$this->patchCVE(); | ||
return parent::install(); | ||
} | ||
|
||
public function uninstall() | ||
{ | ||
$this->unpatchCVE(); | ||
return parent::uninstall(); | ||
} | ||
|
||
/** | ||
* Get the path to the file to patch | ||
* @return string | ||
*/ | ||
private function getFilePath() | ||
{ | ||
return _PS_ROOT_DIR_ . _PS_CLASS_DIR_; | ||
} | ||
|
||
/** | ||
* Apply patch for CVE-2023-30839 | ||
* @return bool | ||
*/ | ||
private function patchCVE() | ||
{ | ||
if ($this->detectAlreadyPatched()) { | ||
return true; | ||
} | ||
|
||
return $this->patchFiles(); | ||
} | ||
|
||
/** | ||
* Remove patch for CVE-2023-30839 | ||
* @return bool | ||
*/ | ||
private function unpatchCVE() | ||
{ | ||
return $this->unpatchFiles(); | ||
} | ||
|
||
/** | ||
* Detect if the patch is already applied | ||
* @return bool | ||
*/ | ||
private function detectAlreadyPatched() | ||
{ | ||
// For each file to patch, check if the patch is already applied | ||
$files_to_patch = $this->getFilesToPatch(); | ||
$base_path = $this->getFilePath(); | ||
|
||
foreach ($files_to_patch as $file_to_patch) { | ||
$path = $base_path . $file_to_patch; | ||
if ($this->detectAlreadyPatchedFile($path, 'CVE-2023-30839')) { | ||
return true; | ||
} | ||
} | ||
|
||
return false; | ||
} | ||
|
||
/** | ||
* Detect if the patch is already applied for a file | ||
* @return bool | ||
*/ | ||
private function detectAlreadyPatchedFile($file, $pattern) | ||
{ | ||
if (file_exists($file)) { | ||
$content = Tools::file_get_contents($file); | ||
if (strpos($content, $pattern) !== false) { | ||
return true; | ||
} | ||
} | ||
return false; | ||
} | ||
|
||
/** | ||
* Get the list of files to patch | ||
* @return array | ||
*/ | ||
private function getPatchFiles() | ||
{ | ||
return glob(dirname(__FILE__) . '/patches/*.patch'); | ||
} | ||
|
||
/** | ||
* Get the list of files to patch | ||
* @return array | ||
*/ | ||
private function getFilesToPatch() | ||
{ | ||
$file_pathes = $this->getPatchFiles(); | ||
foreach ($file_pathes as $file_path) { | ||
$file_name = basename($file_path); | ||
$file_name = str_replace('.patch', '', $file_name); | ||
$files[] = $file_name; | ||
} | ||
return $files; | ||
} | ||
|
||
/** | ||
* Parse a patch file | ||
* @param string $file_path Path to the patch file | ||
* @return array | ||
*/ | ||
private function parsePatchFile($file_path) | ||
{ | ||
$patches = []; | ||
$file = fopen($file_path, 'r'); | ||
while (!feof($file)) { | ||
$line = fgets($file); | ||
$line_patch = explode('¤', $line); | ||
array_push($patches, $line_patch); | ||
} | ||
|
||
return $patches; | ||
} | ||
|
||
/** | ||
* Patches all files | ||
* @return bool | ||
*/ | ||
private function patchFiles() | ||
{ | ||
$files_to_patch = $this->getFilesToPatch(); | ||
$base_path = $this->getFilePath(); | ||
|
||
foreach ($files_to_patch as $file_to_patch) { | ||
$path = $base_path . $file_to_patch; | ||
$patch_file = __DIR__ . '/patches/' . $file_to_patch . '.patch'; | ||
if (!$this->patchFile($path, $patch_file)) { | ||
return false; | ||
} | ||
} | ||
|
||
return true; | ||
} | ||
|
||
/** | ||
* Patches a file | ||
* @param string $path Path to the file to patch | ||
* @param string $patch_file Path to the patch file | ||
* @return bool | ||
*/ | ||
private function patchFile($path, $patch_file) | ||
{ | ||
if (!$this->backupFile($path)) { | ||
return false; | ||
} | ||
|
||
$content = Tools::file_get_contents($path); | ||
$patches_for_file = $this->parsePatchFile($patch_file); | ||
foreach ($patches_for_file as $patch) { | ||
$original = $patch[0]; | ||
$replacement = $patch[1]; | ||
$content = str_replace($original, $replacement, $content); | ||
} | ||
|
||
if (!@file_put_contents($path, $content)) { | ||
return false; | ||
} | ||
|
||
return true; | ||
} | ||
|
||
/** | ||
* Backup the original file | ||
* @param string $path Path to the file to patch | ||
* @return bool | ||
*/ | ||
private function backupFile($path) | ||
{ | ||
$filename = basename($path); | ||
if (!@copy($path, dirname(__FILE__) . '/backup/' . $filename)) { | ||
return false; | ||
} | ||
|
||
return true; | ||
} | ||
|
||
/** | ||
* Restore the original files | ||
* @return bool | ||
*/ | ||
private function unpatchFiles() | ||
{ | ||
$files_to_patch = $this->getFilesToPatch(); | ||
$base_path = $this->getFilePath(); | ||
|
||
foreach ($files_to_patch as $file_to_patch) { | ||
$path = $base_path . $file_to_patch; | ||
$backup_file = __DIR__ . '/backup/' . $file_to_patch; | ||
if (@copy($backup_file, $path)) { | ||
@unlink($backup_file); | ||
} | ||
} | ||
|
||
return true; | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
Deny from all |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,14 @@ | ||
// This method must be used only with queries which display results | ||
if (!preg_match('#^\s*\(?\s*(select|show|explain|describe|desc)\s#i', $sql)) { | ||
if (defined('_PS_MODE_DEV_') && _PS_MODE_DEV_) { | ||
throw new PrestaShopDatabaseException('Db->executeS() must be used only with select, show, explain or describe queries'); | ||
} | ||
|
||
return $this->execute($sql, $use_cache); | ||
} | ||
¤ | ||
// Patch for CVE-2023-30839 | ||
// This method must be used only with queries which display results | ||
if (!preg_match('#^\s*\(?\s*(select|show|explain|describe|desc)\s#i', $sql)) { | ||
throw new PrestaShopDatabaseException('Db->executeS() must be used only with select, show, explain or describe queries'); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,22 @@ | ||
<?php | ||
/** | ||
* 2023 LabelGrup Networks SL | ||
* | ||
* NOTICE OF LICENSE | ||
* | ||
* READ ATTACHED LICENSE.TXT | ||
* | ||
* @author Manel Alonso <[email protected]>, <[email protected]> | ||
* @copyright 2023 LabelGrup Networks SL | ||
* @license LICENSE.TXT | ||
*/ | ||
|
||
header('Expires: Mon, 26 Jul 1997 05:00:00 GMT'); | ||
header('Last-Modified: '.gmdate('D, d M Y H:i:s').' GMT'); | ||
|
||
header('Cache-Control: no-store, no-cache, must-revalidate'); | ||
header('Cache-Control: post-check=0, pre-check=0', false); | ||
header('Pragma: no-cache'); | ||
|
||
header('Location: ../'); | ||
exit; |