Poprawka bezpieczeństwa SUPEE-10752 - Możliwe problemy?


14

Nowa aktualizacja zabezpieczeń Magento 1, rozwiązująca 25 problemów APPSEC

https://magento.com/security/patches/supee-10752

Na jakie typowe problemy należy zwrócić uwagę przy stosowaniu tej poprawki?

SUPEE-10752, Magento Commerce 1.14.3.9 i Open Source 1.9.3.9 zawierają wiele ulepszeń bezpieczeństwa, które pomagają zamknąć uwierzytelnione zdalne wykonywanie kodu administratora (RCE), fałszowanie żądań między witrynami (CSRF) i inne luki w zabezpieczeniach.

Informacje o wszystkich zmianach w wersjach 1.14.3.9 i 1.9.3.9 są dostępne w uwagach do wydania Magento Commerce i Magento Open Source.

Poprawki i aktualizacje są dostępne dla następujących wersji Magento:

Magento Commerce 1.9.0.0-1.14.3.9: SUPEE-10752 lub uaktualnienie do Magento Commerce 1.14.3.9.

Magento Open Source 1.5.0.0-1.9.3.9: SUPEE-10752 lub aktualizacja do Magento Open Source 1.9.3.9.


Szczegółowy opis napotkanego problemu - magento.stackexchange.com/questions/248229/…
Shrenik

Odpowiedzi:


19

Jak wspomniano w oficjalnych dokumentach Magento :

Konflikty podczas instalacji poprawki SUPEE-10752 są najczęściej spowodowane zainstalowaniem wersji 1 poprzedniej łatki ( SUPEE-10570v1 ).

Pamiętaj, aby usunąć SUPEE-10570v1 i zainstalować SUPEE-10570v2 przed instalacją nowego SUPEE-10752.


11

Poniższe pliki są zmieniane / tworzone po zastosowaniu poprawki

app/code/core/Mage/Admin/Model/User.php
app/code/core/Mage/Adminhtml/Block/Catalog/Product/Composite/Fieldset/Options.php
app/code/core/Mage/Adminhtml/Block/Catalog/Product/Edit/Tab/Options/Option.php
app/code/core/Mage/Adminhtml/Block/Widget/Grid/Column/Filter/Datetime.php
app/code/core/Mage/Adminhtml/Model/LayoutUpdate/Validator.php
app/code/core/Mage/Adminhtml/controllers/Catalog/CategoryController.php
app/code/core/Mage/Adminhtml/controllers/Catalog/ProductController.php
app/code/core/Mage/Adminhtml/controllers/Cms/Wysiwyg/ImagesController.php
app/code/core/Mage/Adminhtml/controllers/Cms/WysiwygController.php
app/code/core/Mage/Adminhtml/controllers/CustomerController.php
app/code/core/Mage/Adminhtml/controllers/System/StoreController.php
app/code/core/Mage/Catalog/Model/Product.php
app/code/core/Mage/Catalog/Model/Resource/Category/Tree.php
app/code/core/Mage/Checkout/Model/Api/Resource/Customer.php
app/code/core/Mage/Checkout/Model/Type/Onepage.php
app/code/core/Mage/Checkout/controllers/CartController.php
app/code/core/Mage/Core/Helper/Http.php
app/code/core/Mage/Core/Model/Session/Abstract/Varien.php
app/code/core/Mage/Customer/Helper/Data.php
app/code/core/Mage/Customer/Model/Resource/Customer.php
app/code/core/Mage/Customer/controllers/AccountController.php
app/code/core/Mage/Log/Model/Visitor.php
app/code/core/Mage/Usa/Helper/Data.php
app/code/core/Mage/Usa/Model/Shipping/Carrier/Abstract/Backend/Abstract.php
app/code/core/Mage/Usa/Model/Shipping/Carrier/Ups/Backend/Freemethod.php
app/code/core/Mage/Usa/Model/Shipping/Carrier/Ups/Backend/OriginShipment.php
app/code/core/Mage/Usa/Model/Shipping/Carrier/Ups/Backend/Type.php
app/code/core/Mage/Usa/etc/system.xml
app/code/core/Zend/Filter/PregReplace.php
app/code/core/Zend/Validate/EmailAddress.php
app/design/adminhtml/default/default/template/bundle/product/edit/bundle/option.phtml

app/design/adminhtml/default/default/template/system/shipping/ups.phtml
app/design/frontend/base/default/template/downloadable/catalog/product/links.phtml
app/design/frontend/base/default/template/downloadable/checkout/cart/item/default.phtml
app/design/frontend/base/default/template/downloadable/checkout/onepage/review/item.phtml
app/design/frontend/base/default/template/downloadable/sales/order/items/renderer/downloadable.phtml
app/design/frontend/rwd/default/template/downloadable/checkout/cart/item/default.phtml
app/design/frontend/rwd/default/template/downloadable/checkout/onepage/review/item.phtml
app/design/frontend/rwd/default/template/downloadable/sales/order/items/renderer/downloadable.phtml
app/locale/en_US/Mage_Catalog.csv
app/locale/en_US/Mage_Usa.csv
cron.php
js/tiny_mce/plugins/media/.htaccess
lib/Varien/Image/Adapter/Gd2.php

Do EE Edition dodaje się poniższe pliki inne niż CE

app/code/core/Enterprise/CatalogEvent/Block/Adminhtml/Event/Grid.php
app/code/core/Enterprise/GiftRegistry/Block/Adminhtml/Giftregistry/Edit/Attribute/Attribute.php
app/code/core/Enterprise/GiftRegistry/Model/Attribute/Processor.php
app/code/core/Enterprise/Invitation/Block/Adminhtml/Invitation/Grid.php
app/code/core/Enterprise/Logging/Block/Adminhtml/Details/Renderer/Diff.php
app/code/core/Enterprise/Reward/Block/Adminhtml/Customer/Edit/Tab/Reward/History/Grid/Column/Renderer/Reason.php
app/code/core/Enterprise/TargetRule/Model/Rule.php
app/code/core/Enterprise/TargetRule/controllers/Adminhtml/TargetruleController.php
app/design/adminhtml/default/default/template/enterprise/cms/page/revision/info.phtml

app/design/frontend/enterprise/default/template/cms/hierarchy/pagination.phtml
app/design/frontend/enterprise/iphone/template/downloadable/checkout/cart/item/default.phtml
app/design/frontend/enterprise/iphone/template/downloadable/checkout/onepage/review/item.phtml
app/design/frontend/rwd/enterprise/template/cms/hierarchy/pagination.phtml

app / code / core / Mage / Admin / Model / User.php

+            $sessionUser = $this->getSession()->getUser();
+            if ($sessionUser && $sessionUser->getId() == $this->getId()) {
+                $this->getSession()->setUserPasswordChanged(true);
+            }


+    /**
+     * @return Mage_Admin_Model_Session
+     */
+    protected function getSession()
+    {
+        return  Mage::getSingleton('admin/session');
+    }
+

app / code / core / Mage / Adminhtml / Block / Widget / Grid / Column / Filter / Datetime.php

                     $this->getLocale()->getDateTimeFormat(Mage_Core_Model_Locale::FORMAT_TYPE_SHORT)
                 );
             }
-            return $value;
+            return $this->escapeHtml($value);
         }

-        return parent::getEscapedValue($index);
+        return $this->escapeHtml(parent::getEscapedValue($index));
     }
-
 }

app / code / core / Mage / Adminhtml / controllers / Catalog / CategoryController.php

+            if (isset($data['general']['path'])) {
+                unset($data['general']['path']);
+            }

app / code / core / Mage / Adminhtml / controllers / Catalog / ProductController.php

+                $product->validate();

app / code / core / Mage / Adminhtml / controllers / Cms / Wysiwyg / ImagesController.php

+            $this->getResponse()->setHeader('Content-type', $image->getMimeTypeWithOutFileType());

app / code / core / Mage / Adminhtml / controllers / Cms / WysiwygController.php

+        $this->getResponse()->setHeader('Content-type', $image->getMimeTypeWithOutFileType());

app / code / core / Mage / Adminhtml / controllers / CustomerController.php

+                    $customer->setPasswordCreatedAt(time());

app / code / core / Mage / Adminhtml / controllers / System / StoreController.php

+   /**
+     * Controller predispatch method
+     *
+     * @return Mage_Adminhtml_Controller_Action
+     */
+    public function preDispatch()
+    {
+        $this->_setForcedFormKeyActions(array('deleteWebsitePost', 'deleteGroupPost', 'deleteStorePost'));
+        return parent::preDispatch();
+    }

app / code / core / Mage / Catalog / Model / Product.php

+                        if (!empty($option['file_extension'])) {
+                            $fileExtension = $option['file_extension'];
+                            if (0 !== strcmp($fileExtension, Mage::helper('core')->removeTags($fileExtension))) {
+                                Mage::throwException(Mage::helper('catalog')->__('Invalid custom option(s).'));
+                            }
+                        }

app / code / core / Mage / Catalog / Model / Resource / Category / Tree.php

+            if (!preg_match("#^[0-9\/]+$#", $item['path'])) {
+                $item['path'] = '';
+            }

app / code / core / Mage / Checkout / Model / Api / Resource / Customer.php

+        $customer->setPasswordCreatedAt(time());

Ktoś nadpisuje plik onepage.php, zaktualizuj plik.

app / code / core / Mage / Checkout / Model / Type / Onepage.php

  +        $passwordCreatedTime = $this->_checkoutSession->getData('_session_validator_data')['session_expire_timestamp']
    +            - Mage::getSingleton('core/cookie')->getLifetime();
    +        $customer->setPasswordCreatedAt($passwordCreatedTime);

Dodano weryfikację klucza. Sprawdź, czy formularz koszyka ma klucz formularza

app / code / core / Mage / Checkout / controllers / CartController.php

+        if (!$this->_validateFormKey()) {
+            $this->_redirect('*/*/');
+            return;
+        }
+

app / code / core / Mage / Core / Helper / Http.php

-                if ($this->_getRequest()->getServer($var, false)) {
+                if ($var != 'REMOTE_ADDR' && $this->_getRequest()->getServer($var, false)) {

+        if (strpos($this->_remoteAddr, ',') !== false) {
+            $ipList = explode(',', $this->_remoteAddr);
+            $this->_remoteAddr = trim(reset($ipList));
+        }
+

app / code / core / Mage / Core / Model / Session / Abstract / Varien.php

+    const VALIDATOR_PASSWORD_CREATE_TIMESTAMP   = 'password_create_timestamp';

+    /**
+     * Use password creation timestamp in validator key
+     *
+     * @return bool
+     */
+    public function useValidateSessionPasswordTimestamp()
+    {
+        return true;
+    }
+

+        if ($this->useValidateSessionPasswordTimestamp()
+            && isset($validatorData[self::VALIDATOR_PASSWORD_CREATE_TIMESTAMP])
+            && isset($sessionData[self::VALIDATOR_SESSION_EXPIRE_TIMESTAMP])
+            && $validatorData[self::VALIDATOR_PASSWORD_CREATE_TIMESTAMP]
+            > $sessionData[self::VALIDATOR_SESSION_EXPIRE_TIMESTAMP] - $this->getCookie()->getLifetime()
+        ) {
+            return false;
+        }

+        if (isset($this->_data['visitor_data']['customer_id'])) {
+            $parts[self::VALIDATOR_PASSWORD_CREATE_TIMESTAMP] =
+                Mage::helper('customer')->getPasswordTimestamp($this->_data['visitor_data']['customer_id']);
+        }
+

app / code / core / Mage / Customer / Helper / Data.php

+    /**
+     * Get customer password creation timestamp or customer account creation timestamp
+     *
+     * @param $customerId
+     * @return int
+     */
+    public function getPasswordTimestamp($customerId)
+    {
+        /** @var $customer Mage_Customer_Model_Customer */
+        $customer = Mage::getModel('customer/customer')
+            ->setWebsiteId(Mage::app()->getStore()->getWebsiteId())
+            ->load((int)$customerId);
+        $passwordCreatedAt = $customer->getPasswordCreatedAt();
+
+        return is_null($passwordCreatedAt) ? $customer->getCreatedAtTimestamp() : $passwordCreatedAt;
+    }
+

app / code / core / Mage / Customer / Model / Resource / Customer.php

-        $customer->setPassword($newPassword);
+        $customer->setPassword($newPassword)->setPasswordCreatedAt(time());
+        $this->saveAttribute($customer, 'password_created_at');
app/code/core/Mage/Customer/controllers/AccountController.php

+                $customer->setPasswordCreatedAt(time());



-        if (!$this->getCustomerId() && $customer = $observer->getEvent()->getCustomer()) {
+        if ($customer = $observer->getEvent()->getCustomer()) {

> app/code/core/Mage/Log/Model/Visitor.php

    -        if (!$this->getCustomerId() && $customer = $observer->getEvent()->getCustomer()) {
    +        if ($customer = $observer->getEvent()->getCustomer()) {

app / code / core / Mage / Usa / Helper / Data.php

+
+    /**
+     * Validate ups type value
+     *
+     * @param $valueForCheck string ups type value for check
+     *
+     * @return bool
+     */
+    public function validateUpsType($valueForCheck) {
+        $result = false;
+        $sourceModel = Mage::getSingleton('usa/shipping_carrier_ups_source_type');
+        foreach ($sourceModel->toOptionArray() as $allowedValue) {
+            if (isset($allowedValue['value']) && $allowedValue['value'] == $valueForCheck) {
+                $result = true;
+                break;
+            }
+        }
+        return $result;
+    }
 }

cron.php

cron.php: uchwyt wyjątku w pliku cron.php

-Mage::app('admin')->setUseSessionInUrl(false);
+try {
+    Mage::app('admin')->setUseSessionInUrl(false);
+} catch (Exception $e) {
+    Mage::printException($e);
+    exit;
+}

lib / Varien / Image / Adapter / Gd2.php

GD2: zwraca prawdziwy typ MIME.

+        header("Content-type: ".$this->getMimeTypeWithOutFileType());

+
+    /**
+     * Gives real mime-type with not considering file type field
+     *
+     * @return string
+     */
+    public function getMimeTypeWithOutFileType()
+    {
+        return $this->_fileMimeType;
+    }
 }

js / tiny_mce / plugins / media / .htaccess

Jeśli używasz nginx zamiast Apache, upewnij się, że zaktualizowałeś konfigurację, aby powielić tę zmianę.

+<IfModule mod_rewrite.c>
+    <Files moxieplayer.swf>
+        RewriteEngine on
+        RewriteCond %{QUERY_STRING} !^$
+        RewriteRule ^(.*)$ %{REQUEST_URI}? [R=301,L]
+    </Files>
+</IfModule>

app / design / adminhtml / default / default / template / system / shipping / ups.phtml

+if (!in_array($storedOriginShipment, array_keys($orShipArr))) {
+    $storedOriginShipment = '';
+}

+if ($storedFreeShipment != '' && !in_array($storedFreeShipment, array_keys($defShipArr))) {
+    $storedFreeShipment = '';
+}

+if (!Mage::helper('usa')->validateUpsType($storedUpsType)) {
+    $storedUpsType = '';
+}

Metody wysyłki nowo dodane / zaktualizowane pliki to:

app/code/core/Mage/Usa/Helper/Data.php
app/code/core/Mage/Usa/Model/Shipping/Carrier/Abstract/Backend/Abstract.php
app/code/core/Mage/Usa/Model/Shipping/Carrier/Ups/Backend/Freemethod.php
app/code/core/Mage/Usa/Model/Shipping/Carrier/Ups/Backend/OriginShipment.php
app/code/core/Mage/Usa/Model/Shipping/Carrier/Ups/Backend/Type.php

Pliki Escapehtml:

Pliki interfejsu użytkownika do pobrania: każdy, kto korzysta z produktu do pobrania, zaktualizuj pliki w plikach motywu.

app / design / frontend / base / default / template / downloadable / catalog / product / links.phtml

Sprawdź kod

<dt><label<?php if ($_isRequired) echo ' class="required"' ?>><?php if ($_isRequired) echo '<em>*</em>' ?><?php echo
    > $this->getLinksTitle() ?></label></dt>

Zamienić

<dt><label<?php if ($_isRequired) echo ' class="required"' ?>><?php if ($_isRequired) echo '<em>*</em>' ?><?php echo
    > $this->escapeHtml($this->getLinksTitle()); ?></label></dt>

app / design / frontend / base / default / template / downloadable / checkout / cart / item / default.phtml

Sprawdź kod

<dt><?php echo $this->getLinksTitle() ?></dt>

Zamienić

 <dt><?php echo $this->escapeHtml($this->getLinksTitle()); ?></dt>

app / design / frontend / base / default / template / downloadable / sales / order / items / renderer / downloadable.phtml

Sprawdź kod

<dt><?php echo $this->getLinksTitle() ?></dt>

Zamienić

<dt><?php echo $this->escapeHtml($this->getLinksTitle()); ?></dt>

app / design / frontend / default / iphone / template / downloadable / checkout / cart / item / default.phtml

Sprawdź kod

<dt><?php echo $this->getLinksTitle() ?></dt>

Zamienić

<dt><?php echo $this->escapeHtml($this->getLinksTitle()); ?></dt>

app / design / frontend / default / iphone / template / downloadable / checkout / onepage / review / item.phtml Sprawdź kod

`<dt><?php echo $this->getLinksTitle() ?></dt>`

Zamienić

`<dt><?php echo $this->escapeHtml($this->getLinksTitle()); ?></dt>`

app / design / frontend / rwd / default / template / downloadable / checkout / cart / item / default.phtml Sprawdź kod

`<dt><?php echo $this->getLinksTitle() ?></dt>`

Zamienić

`<dt><?php echo $this->escapeHtml($this->getLinksTitle()); ?></dt>`

app / design / frontend / rwd / default / template / downloadable / checkout / onepage / review / item.phtml

Sprawdź kod

<dt><?php echo $this->getLinksTitle() ?></dt>

Zamienić

<dt><?php echo $this->escapeHtml($this->getLinksTitle()); ?></dt>

app / design / frontend / rwd / default / template / downloadable / sales / order / items / renderer / downloadable.phtml

Sprawdź kod

<dt><?php echo $this->getLinksTitle() ?></dt>

Zamienić

<dt><?php echo $this->escapeHtml($this->getLinksTitle()); ?></dt>

Inne pliki Escapehtml:

app / code / core / Mage / Adminhtml / Block / Catalog / Product / Composite / Fieldset / Options.php

+        if (!empty($option['file_extension'])) {
+            $option['file_extension'] = $this->escapeHtml($option['file_extension']);
+        }

app / code / core / Mage / Adminhtml / Block / Catalog / Product / Edit / Tab / Options / Option.php

-                    $value['file_extension'] = $option->getFileExtension();
+                    $value['file_extension'] = $this->escapeHtml($option->getFileExtension());

app / design / frontend / enterprise / default / template / cms / hierarchy / pagination.phtml

-    <li><a title="<?php echo $this->escapeHtml($node->getLabel())?>" href="<?php echo $node->getUrl()?>"><?php echo $this->getNodeLabel($node)?></a></li>

+    <li><a title="<?php echo $this->escapeHtml($node->getLabel())?>" href="<?php echo $node->getUrl()?>"><?php echo $this->escapeHtml($this->getNodeLabel($node)); ?></a></li>

w app / code / core / Mage / Checkout / controllers / CartController.php, na której stronie w kasie zazwyczaj występuje błąd klucza formularza?
Ikona

1
Nie widzę żadnego błędu klucza formularza. jeśli ktoś nadpisuje domyślny plik / template / checkout / cart.phtml i brakuje klucza form form. przekieruje stronę główną nie przez błąd. to jest lista kontrolna. jeśli wystąpi błąd, sprawdź klucz formularza :). Dzięki za zadawanie pytań :)
Rama Chandran M

1
Nie wydaje mi się, żeby umieszczanie wszystkich różnic łatek tutaj było bardzo przydatne. Bardziej interesują mnie rzeczywiste możliwe problemy ...
7ochem

1
Dziękuję za komentarz. Uważam, że jest to przydatne dla innych, ponieważ łatwo jest znaleźć zmiany plików i zmiany kodu podstawowego. Przykładowa aplikacja / design / frontend / rwd / default / template / downloadable / checkout / onepage / review / item.phtml załóżmy, że nadpisujemy w twoim temacie, po prostu zmieniamy kod łatwo, to bardziej przypomina listę kontrolną.
Rama Chandran M

8

Modyfikacja przeciążonej filtermetody w Zend_Filter_PregReplacejest naiwna i zakłada, że $this->_matchPatternzawsze jest to ciąg znaków. Ta właściwość jest następnie dostarczana jako pierwszy argument do preg_replace. W rzeczywistości tablica jest również całkowicie poprawnym argumentem. Fakt ten jest wykorzystywany przez wiele podstawowych Zend_Filterklas (takich jak Zend_Filter_Word_SeparatorToCamelCase). Tak więc każde rozszerzenie / gałąź kodu, która używa tego filtra lub jednego z jego pochodnych, z argumentem tablicowym _matchPattern, zacznie rzucać Warning: substr() expects parameter 1 to be a string, array given.

Prostym przykładem tego, co prawdopodobnie powinien zrobić, byłoby coś w stylu:

/**
 * Perform regexp replacement as filter
 *
 * @param  string $value
 * @return string
 */
public function filter($value)
{
    if ($this->_matchPattern == null) {
        #require_once 'Zend/Filter/Exception.php';
        throw new Zend_Filter_Exception(get_class($this) . ' does not have a valid MatchPattern set.');
    }

    $patterns = is_array($this->_matchPattern) ? $this->_matchPattern : array($this->_matchPattern);
    foreach ($patterns as $pattern) {
        if ($this->_containsEvalModifier($pattern)) {
            throw new Zend_Filter_Exception(get_class($this) . ' uses deprecated modifier "/e".');
        }
    }

    return preg_replace($this->_matchPattern, $this->_replacement, $value);
}

/**
 * Check if the modifiers contains the eval flag.
 *
 * @param  string $value
 * @return bool
 */
protected function _containsEvalModifier($pattern)
{
    $firstDelimiter = substr($pattern, 0, 1);
    $partsOfRegex = explode($firstDelimiter, $pattern);
    $modifiers = array_pop($partsOfRegex);

    return ($modifiers != str_replace('e', '', $modifiers));
}

Chociaż nie przeprowadziłem jeszcze dokładnych testów tego.

EDYCJA: Warto zauważyć, że chociaż powyższe proponowane rozwiązanie powinno zapobiegać błędom, wdrożenie jest technicznie nadal nieco naiwne i podatne na fałszywe alarmy. Zakłada się, że ogranicznik wyrażenia regularnego oddzielający wzorzec od modyfikatorów jest taki sam, jak ten na początku łańcucha. Technicznie nie musi tak być, ponieważ PHP obsługuje różne ograniczniki w stylu nawiasów. Dlatego prawidłowe dane wejściowe {hello}isokreślą, że modyfikatory są hello}is(a nie rzeczywistymi modyfikatorami is), a tym samym zgłoszą wyjątek, nawet jeśli wzorzec faktycznie nie zawiera emodyfikatora.


5

1.7.0.2 Problem z wersją: po zainstalowaniu łatki i przejściu do kasy na jednej stronie (ogólne kasy Magento), otrzymaj ten błąd

Błąd analizy: błąd składni, nieoczekiwany

app / code / core / Mage / Checkout / Model / Type / Onepage.php w linii 691

Podczas cofania poprawki błąd znika.

Zagłębiając się w to pytanie, zauważyłem, że łatka dodała następujący wiersz do pliku onepage.php.

$passwordCreatedTime = $this->_checkoutSession->getData('_session_validator_data')['session_expire_timestamp']
            - Mage::getSingleton('core/cookie')->getLifetime();
        $customer->setPasswordCreatedAt($passwordCreatedTime);

ROZWIĄZANIE: Dzięki @FabianSchmengler

AKTUALIZACJA DO PHP w wersji 5.4 i nowszych!


zastosowałem również łatę oryginalną, będzie to $ passwordCreatedTime = $ this -> _ checkoutSession-> getData ('_ session_validator_data') ['session_expire_timestamp'] - Mage :: getSingleton ('core / cookie') -> getLifetime (); następny wiersz (nowa linia utworzona / dodana) - Mage :: getSingleton ('core / cookie') -> getLifetime (); powstała przyczyna problemu
Rama Chandran M

@RamaChandranM Tak! Otrzymujesz ten sam błąd PARSE? Której wersji używasz?
Ikona

1
tak, sprawdzę inny projekt i podam więcej szczegółów Ans :)
Rama Chandran M

2
@Icon była łatka na kompatybilność z PHP 5.4. Długo nie dotknąłem żadnej instalacji 1.7, ale spodziewam się, że zadziała również na wersji 5.6, spróbuj.
Fabian Schmengler

1
@icon na razie możesz zignorować powiadomienia o wycofaniu, stanie się to istotne, gdy zaktualizujesz do PHP 7
Fabian Schmengler

2

Znana kwestia :-

Jeśli Twój niestandardowy kod lub rozszerzenie używa Zend/Filter/PregReplace.php wraz z modyfikatorem e, zwróci teraz błąd z powodu możliwych problemów RCE.

Ta poprawka jest poniżej bezpieczeństwa.

1) Dodatkowa zmiana hasła sprawdzania poprawności sesji administratora

+++ app/code/core/Mage/Admin/Model/User.php

+            $sessionUser = $this->getSession()->getUser();
+            if ($sessionUser && $sessionUser->getId() == $this->getId()) {
+                $this->getSession()->setUserPasswordChanged(true);
+            }

i wtedy

+    /**
+     * @return Mage_Admin_Model_Session
+     */
+    protected function getSession()
+    {
+        return  Mage::getSingleton('admin/session');
+    }
+

class Mage_Admin_Model_User

+        $oldPassword = $this->getPassword();
     $this->setId(null);
     $this->load($id);
+        $isUserPasswordChanged = $this->getSession()->getUserPasswordChanged();
+        if ($this->getPassword() !== $oldPassword && !$isUserPasswordChanged) {
+            $this->setId(null);
+        } elseif ($isUserPasswordChanged) {
+            $this->getSession()->setUserPasswordChanged(false);
+        }

2) Sprawdzanie poprawności rozszerzenia pliku

app/code/core/Mage/Adminhtml/Block/Catalog/Product/Composite/Fieldset/Options.php

+        if (!empty($option['file_extension'])) {
+            $option['file_extension'] = $this->escapeHtml($option['file_extension']);
+        }

app/code/core/Mage/Adminhtml/Block/Catalog/Product/Edit/Tab/Options/Option.php app/code/core/Mage/Adminhtml/Block/Catalog/Product/Edit/Tab/Options/Option.php

-                    $value['file_extension'] = $option->getFileExtension();
+                    $value['file_extension'] = $this->escapeHtml($option->getFileExtension());

app/code/core/Mage/Catalog/Model/Product.php

+                        if (!empty($option['file_extension'])) {
+                            $fileExtension = $option['file_extension'];
+                            if (0 !== strcmp($fileExtension, Mage::helper('core')->removeTags($fileExtension))) {
+                                Mage::throwException(Mage::helper('catalog')->__('Invalid custom option(s).'));
+                            }
+                        }

3) Dodano HTML Escape dla XSS

+++ app/code/core/Mage/Adminhtml/Block/Widget/Grid/Column/Filter/Datetime.php

-            return $value;
+            return $this->escapeHtml($value);
     }

-        return parent::getEscapedValue($index);
+        return $this->escapeHtml(parent::getEscapedValue($index));

app/design/frontend/base/default/template/downloadable/catalog/product/links.phtml

-        <dt><label<?php if ($_isRequired) echo ' class="required"' ?>><?php if ($_isRequired) echo '<em>*</em>' ?><?php echo $this->getLinksTitle() ?></label></dt>
+        <dt><label<?php if ($_isRequired) echo ' class="required"' ?>><?php if ($_isRequired) echo '<em>*</em>' ?><?php echo $this->escapeHtml($this->getLinksTitle()); ?></label></dt>

app/design/frontend/base/default/template/downloadable/checkout/cart/item/default.phtml

-            <dt><?php echo $this->getLinksTitle() ?></dt>
+            <dt><?php echo $this->escapeHtml($this->getLinksTitle()); ?></dt>

app/design/frontend/base/default/template/downloadable/checkout/onepage/review/item.phtml

-            <dt><?php echo $this->getLinksTitle() ?></dt>
+            <dt><?php echo $this->escapeHtml($this->getLinksTitle()); ?></dt>

app/design/frontend/base/default/template/downloadable/sales/order/items/renderer/downloadable.phtml

-            <dt><?php echo $this->getLinksTitle() ?></dt>
+            <dt><?php echo $this->escapeHtml($this->getLinksTitle()); ?></dt>

app/design/frontend/default/iphone/template/downloadable/checkout/onepage/review/item.phtml

-                <dt><?php echo $this->getLinksTitle() ?></dt>
+                <dt><?php echo $this->escapeHtml($this->getLinksTitle()); ?></dt>

app/design/frontend/rwd/default/template/downloadable/checkout/cart/item/default.phtml

-            <dt><?php echo $this->getLinksTitle() ?></dt>
+            <dt><?php echo $this->escapeHtml($this->getLinksTitle()); ?></dt>

app/design/frontend/rwd/default/template/downloadable/checkout/onepage/review/item.phtml

-            <dt><?php echo $this->getLinksTitle() ?></dt>
+            <dt><?php echo $this->escapeHtml($this->getLinksTitle()); ?></dt>

app/design/frontend/rwd/default/template/downloadable/sales/order/items/renderer/downloadable.phtml

-            <dt><?php echo $this->getLinksTitle() ?></dt>
+            <dt><?php echo $this->escapeHtml($this->getLinksTitle()); ?></dt>

4) Wyrażenie XPath do sprawdzania aktualizacji układu

app/code/core/Mage/Adminhtml/Model/LayoutUpdate/Validator.php

+    /**
+     * XPath expression for checking layout update
+     *
+     * @var array
+     */
+    protected $_disallowedXPathExpressions = array(
+        '*//template',
+        '*//@template',
+        '//*[@method=\'setTemplate\']',
+        '//*[@method=\'setDataUsingMethod\']//*[text() = \'template\']/../*'
+    );
+

Mage_Adminhtml_Model_LayoutUpdate_Validator

-        if ($templatePaths = $value->xpath('*//template | *//@template | //*[@method=\'setTemplate\']/*')) {
+        if ($templatePaths = $value->xpath($this->_getXpathValidationExpression())) {

Mage_Adminhtml_Model_LayoutUpdate_Validator

+    /**
+     * Returns xPath for validate incorrect path to template
+     *
+     * @return string xPath for validate incorrect path to template
+     */
+    protected function _getXpathValidationExpression() {
+        return implode(" | ", $this->_disallowedXPathExpressions);
+    }
+



+    /**
+     * Returns xPath for validate incorrect path to template
+     *
+     * @return string xPath for validate incorrect path to template
+     */
+    protected function _getXpathValidationExpression() {
+        return implode(" | ", $this->_disallowedXPathExpressions);
+    }
+

app/code/core/Mage/Catalog/Model/Resource/Category/Tree.php

+            if (!preg_match("#^[0-9\/]+$#", $item['path'])) {
+                $item['path'] = '';
+            }

5) Uwierzytelniony zastrzyk SQL podczas zapisywania kategorii

app/code/core/Mage/Adminhtml/controllers/Catalog/CategoryController

+            if (isset($data['general']['path'])) {
+                unset($data['general']['path']);
+            }

6) Sprawdź poprawność produktu app/code/core/Mage/Adminhtml/controllers/Catalog/ProductController.php

+                $product->validate();

7) typ mimetyczny app/code/core/Mage/Adminhtml/controllers/Cms/Wysiwyg/ImagesController.php

+            $this->getResponse()->setHeader('Content-type', $image->getMimeTypeWithOutFileType());

app/code/core/Mage/Adminhtml/controllers/Cms/WysiwygController.php

+        $this->getResponse()->setHeader('Content-type', $image->getMimeTypeWithOutFileType());

lib/Varien/Image/Adapter/Gd2.php

-        header("Content-type: ".$this->getMimeType());
+        header("Content-type: ".$this->getMimeTypeWithOutFileType());


+
+    /**
+     * Gives real mime-type with not considering file type field
+     *
+     * @return string
+     */
+    public function getMimeTypeWithOutFileType()
+    {
+        return $this->_fileMimeType;
+    }

8) Utworzono hasło klienta app/code/core/Mage/Adminhtml/controllers/CustomerController.php

+                    $customer->setPasswordCreatedAt(time());

app/code/core/Mage/Checkout/Model/Api/Resource/Customer.php

+        $customer->setPasswordCreatedAt(time());

app/code/core/Mage/Checkout/Model/Type/Onepage.php

+        $passwordCreatedTime = $this->_checkoutSession->getData('_session_validator_data')['session_expire_timestamp']
+            - Mage::getSingleton('core/cookie')->getLifetime();
+        $customer->setPasswordCreatedAt($passwordCreatedTime);

app/code/core/Mage/Core/Model/Session/Abstract/Varien.php

+    const VALIDATOR_PASSWORD_CREATE_TIMESTAMP   = 'password_create_timestamp';


+    /**
+     * Use password creation timestamp in validator key
+     *
+     * @return bool
+     */
+    public function useValidateSessionPasswordTimestamp()
+    {
+        return true;
+    }


+        if ($this->useValidateSessionPasswordTimestamp()
+            && isset($validatorData[self::VALIDATOR_PASSWORD_CREATE_TIMESTAMP])
+            && isset($sessionData[self::VALIDATOR_SESSION_EXPIRE_TIMESTAMP])
+            && $validatorData[self::VALIDATOR_PASSWORD_CREATE_TIMESTAMP]
+            > $sessionData[self::VALIDATOR_SESSION_EXPIRE_TIMESTAMP] - $this->getCookie()->getLifetime()
+        ) {
+            return false;
+        }

app/code/core/Mage/Customer/Helper/Data.php

+    /**
+     * Get customer password creation timestamp or customer account creation timestamp
+     *
+     * @param $customerId
+     * @return int
+     */
+    public function getPasswordTimestamp($customerId)
+    {
+        /** @var $customer Mage_Customer_Model_Customer */
+        $customer = Mage::getModel('customer/customer')
+            ->setWebsiteId(Mage::app()->getStore()->getWebsiteId())
+            ->load((int)$customerId);
+        $passwordCreatedAt = $customer->getPasswordCreatedAt();
+
+        return is_null($passwordCreatedAt) ? $customer->getCreatedAtTimestamp() : $passwordCreatedAt;
+    }
+

app/code/core/Mage/Customer/Model/Resource/Customer.php

-        $customer->setPassword($newPassword);
+        $customer->setPassword($newPassword)->setPasswordCreatedAt(time());
     $this->saveAttribute($customer, 'password_hash');
+        $this->saveAttribute($customer, 'password_created_at');

app/code/core/Mage/Customer/controllers/AccountController.php

+                $customer->setPasswordCreatedAt(time());

Mage_Customer_AccountController

+            $customer->setPasswordCreatedAt(time());
         $customer->save();

``

+                $customer->setPasswordCreatedAt(time());

app/code/core/Mage/Log/Model/Visitor.php

-        if (!$this->getCustomerId() && $customer = $observer->getEvent()->getCustomer()) {
+        if ($customer = $observer->getEvent()->getCustomer()) {

9) Zmiany UPS

app/code/core/Mage/Usa/Helper/Data.php

+
+    /**
+     * Validate ups type value
+     *
+     * @param $valueForCheck string ups type value for check
+     *
+     * @return bool
+     */
+    public function validateUpsType($valueForCheck) {
+        $result = false;
+        $sourceModel = Mage::getSingleton('usa/shipping_carrier_ups_source_type');
+        foreach ($sourceModel->toOptionArray() as $allowedValue) {
+            if (isset($allowedValue['value']) && $allowedValue['value'] == $valueForCheck) {
+                $result = true;
+                break;
+            }
+        }
+        return $result;
+    }

DODANO pliki dla UPS

`app/code/core/Mage/Usa/Model/Shipping/Carrier/Abstract/Backend/Abstract.php` 
`app/code/core/Mage/Usa/Model/Shipping/Carrier/Ups/Backend/Freemethod.php`
`app/code/core/Mage/Usa/Model/Shipping/Carrier/Ups/Backend/OriginShipment.php`
`app/code/core/Mage/Usa/Model/Shipping/Carrier/Ups/Backend/Type.php`

Dodano ustawienie dla tej nowej funkcji

app/code/core/Mage/Usa/etc/system.xml

+                            <backend_model>usa/shipping_carrier_ups_backend_freemethod</backend_model>

843 linia

+                            <backend_model>usa/shipping_carrier_ups_backend_originShipment</backend_model>

886

+                            <backend_model>usa/shipping_carrier_ups_backend_type</backend_model>

app/design/adminhtml/default/default/template/system/shipping/ups.phtml

+if (!in_array($storedOriginShipment, array_keys($orShipArr))) {
+    $storedOriginShipment = '';
+}
+if ($storedFreeShipment != '' && !in_array($storedFreeShipment, array_keys($defShipArr))) {
+    $storedFreeShipment = '';
+}
+if (!Mage::helper('usa')->validateUpsType($storedUpsType)) {
+    $storedUpsType = '';
+}
 ?>

10) Dodano klasę Zend

`app/code/core/Zend/Filter/PregReplace.php`
`app/code/core/Zend/Validate/EmailAddress.php`

1> 1) Walidacja produktu w pakiecie

app/design/adminhtml/default/default/template/bundle/product/edit/bundle/option.phtml

+    <?php $_selection->setSku($this->escapeHtml($_selection->getSku())); ?>

12) Sesja administracyjna w try catch w cron.php

-Mage::app('admin')->setUseSessionInUrl(false);
+try {
+    Mage::app('admin')->setUseSessionInUrl(false);
+} catch (Exception $e) {
+    Mage::printException($e);
+    exit;
+}

2

Wygląda na to, że częścią poprawki jest htmlEscaping wszystkich „getLinksTitle ()”. Ale zapomnieli o następujących plikach (jest to oparte na 1.8.1).

app/design/frontend/base/default/template/downloadable/checkout/multishipping/item/downloadable.phtml

app/design/frontend/base/default/template/downloadable/email/order/items/creditmemo/downloadable.phtml

app/design/frontend/base/default/template/downloadable/email/order/items/invoice/downloadable.phtml

app/design/frontend/base/default/template/downloadable/email/order/items/order/downloadable.phtml

app/design/frontend/base/default/template/downloadable/sales/order/creditmemo/items/renderer/downloadable.phtml

app/design/frontend/base/default/template/downloadable/sales/order/invoice/items/renderer/downloadable.phtml

app/design/frontend/default/iphone/template/downloadable/sales/order/creditmemo/items/renderer/downloadable.phtml

app/design/frontend/default/iphone/template/downloadable/sales/order/invoice/items/renderer/downloadable.phtml

2

Łatka nie działa na waniliowym Magento CE 1.8.0.0

Aktualizacja: Dodano rozwiązanie poniżej.

Problem:

file app/design/frontend/base/default/template/downloadable/sales/order/items/renderer/downloadable.phtml
Hunk #1 FAILED at 54.

Zastosowane poprzednie łaty:

  • APPSEC-212
  • SUPEE-2619
  • SUPEE-2725
  • SUPEE-3941
  • SUPEE-5344
  • SUPEE-5994
  • SUPEE-6237
  • SUPEE-6285
  • SUPEE-6482
  • SUPEE-6788
  • SUPEE-7405
  • SUPEE-7405v.1.1
  • SUPEE-7616
  • SUPEE-8167
  • SUPEE-8788v2
  • SUPEE-8967
  • SUPEE-9652
  • SUPEE-9767v2
  • SUPEE-10336
  • SUPEE-10266
  • SUPEE-10415
  • SUPEE-10570v2

Rozwiązanie

Naprawiono przez edycję pliku łatki. Łatka zastąpiona downloadable.phtmlprzez tę z łatki, ponieważ v1.7.0.2w oryginalnym pliku łatek są to linie 1854–1862.

Wynika to głównie z wcięcia w pliku. Jak zmiany downloadable.phtmlwV1.7.0.2 wprowadzono więcej wcięć.

Rozwiązanie 2

Miałem podobny problem, ale udało mi się naprawić, ponownie zapisując oryginalny plik w edytorze, który wymusił zakończenie linii na LF w stylu uniksowym, a nie na CRLF w stylu Windows lub na Mac CR


1

W odniesieniu do Matta Antleya, być może nie uwzględnili z tego powodu SUPEE-10570v2

Magento został niedawno poinformowany o problemie zarówno z poprawką SUPEE-10570>, jak i wersjami Magento 1.9.3.8/1.14.3.8, który może spowodować niemożność> dokonania przez klientów> dokonania transakcji przy próbie rejestracji. Magento udostępnia teraz zaktualizowaną łatkę (SUPEE-10570v2), która> nie powoduje już tego problemu. Należy jednak pamiętać, że ta nowa łatka już nie chroni> przed dwoma problemami bezpieczeństwa związanymi z obsługą sesji niskiego ryzyka, przed którymi łata zabezpieczona jest SUPEE-10570. https://magento.com/security/patches/supee-10570

O ile wiem, błąd kasy nie był bardzo częsty, więc postanowili zostać przy SUPEE-10570, który chroni przed dwoma problemami bezpieczeństwa niskiego ryzyka ?!


+1 To najprawdopodobniej powód, dla którego warto zauważyć, że jeśli użytkownicy dokonają aktualizacji i będą musieli złożyć wniosek SUPEE-10570v2, będą musieli go ponownie zastosować.
Matt Antley,

Jak stwierdził Peter O'Callaghan, zmiany z 10570v2 są cofane o 10752, więc nie trzeba uwzględniać tego pierwszego. Ponieważ w wersji 1.9.3.9 nie ma wersji 10570v2, nie należy niczego stosować. Całe rozumowanie jest słabe: dlaczego Magento powinien utrzymywać swoją gałąź 1.9.3.9 na innej podstawie niż wszystkie inne? Powiedzieli nawet, że będą opierać każdą przyszłą wersję i łatkę na 10570v2.
pong

Dzięki za komentarze Peter i pong. Usunąłem moją odpowiedź, ponieważ jest ona myląca, jak stwierdzili oboje. To nie była moja intencja, tylko coś, o czym nie myślałem, pisząc to i było to coś, co krótko zauważyłem, kiedy na niego spojrzałem SUPEE-10752i podskoczyłem trochę z pistoletu. Jeszcze raz dziękuję za komentarze.
Matt Antley,

1

Łatka nie działa na waniliowym Magento CE 1.6.0.0

Aktualizacja: Dodano rozwiązanie poniżej.

Problemy:

file app/code/core/Mage/Admin/Model/User.php
Hunk #1 FAILED at 127.
...
file app/code/core/Mage/Customer/controllers/AccountController.php
Hunk #2 FAILED at 812.

Zastosowane poprzednie łaty:

  • APPSEC-212
  • SUPEE-2631
  • SUPEE-2725
  • SUPEE-5344
  • SUPEE-5994
  • SUPEE-6237
  • SUPEE-6285
  • SUPEE-6482
  • SUPEE-6788
  • SUPEE-7405
  • SUPEE-7405v.1.1
  • SUPEE-8167
  • SUPEE-8788v2
  • SUPEE-8967
  • SUPEE-9652
  • SUPEE-9767v2
  • SUPEE-10266
  • SUPEE-10415
  • SUPEE-10570v2
  • SUPEE-10752

Rozwiązany

Rozwiązałem ten problem, zmieniając plik łatki. Zastąpiłem porcje, które dały problemy, odpowiednimi z łatki do wersji 1.5.1.0. W oryginalnym pliku łatki są to linie 167-177 i 663-670.


1

W EE v1.14.2.4 po zastosowaniu SUPEE-10752 musiałem również zastosować następującą łatkę, aby naprawić problem polegający na tym, że kasa przekierowuje na stronę główną zamiast strony sukcesu:

Plik: invalid_session_fix-2018-03-14-05-10-19.patch

diff --git a/app/code/core/Mage/Core/Model/Session/Abstract/Varien.php b/app/code/core/Mage/Core/Model/Session/Abstract/Varien.php
index 59b3ea8..35155f1 100644
--- a/app/code/core/Mage/Core/Model/Session/Abstract/Varien.php
+++ b/app/code/core/Mage/Core/Model/Session/Abstract/Varien.php
@@ -485,7 +485,7 @@ class Mage_Core_Model_Session_Abstract_Varien extends Varien_Object
             && isset($validatorData[self::VALIDATOR_PASSWORD_CREATE_TIMESTAMP])
             && isset($sessionData[self::VALIDATOR_SESSION_EXPIRE_TIMESTAMP])
             && $validatorData[self::VALIDATOR_PASSWORD_CREATE_TIMESTAMP]
-            > $sessionData[self::VALIDATOR_SESSION_EXPIRE_TIMESTAMP] - $this->getCookie()->getLifetime()
+            > $sessionData[self::VALIDATOR_SESSION_EXPIRE_TIMESTAMP]
         ) {
             return false;
         }

Powyższa poprawka znajduje się w https://magento.com/tech-resources/download pod SUPEE-10570 > invalid_session_fix.patch (0 MB)


To samo robi z CE 1.9.3.6, gdy php jest <5,5, dzięki za poprawkę
GunJan Mehta

1

Po tej łatce napotkałem problem. Nie mogę ustawić „darmowej metody” dla „UPS Type” „United Parcel Service XML”. Magento zgłasza błąd po wybraniu dowolnej metody w menu rozwijanym „Metoda bezpłatna”. Błąd: „ Field” Ups Free Method ”ma niepoprawną wartość.

Czy ktoś napotkał ten sam problem i ma rozwiązanie?

Z góry dziękuję!


0

W wersji 1.6 łatka ups.phtml jest uszkodzona. Odwołuje się do $ przechowywaneOriginShipment, $ przechowywaneFreeShipment, które mają literówkę w 1.6 ($ stroredOriginShipment i $ stroredFreeShipment). Ponadto odwołuje się do $ przechowywaneUpsType, który w ogóle nie istnieje w wersji 1.6.


0

Napotkaliśmy problem w wersjach 1.9.1.0 i 1.9.2.4 (nie testowałem na innych). Nie pojawia się we wszystkich naszych projektach, ale powtórzył się w kilku z nich. Uważamy, że może to wpływać na projekty, które miały kiedyś zainstalowany SUPEE-10570v1.

Po zastosowaniu poprawki, jeśli użytkownik się zaloguje, zobaczy stronę swojego konta w porządku. Jeśli jednak spróbują wrócić do dowolnej innej strony w witrynie, strona przestanie odpowiadać i zobaczy albo pusty ekran lub 502 Bad Gateway. Wynika to z tego, że PHP przechodzi w nieskończoną pętlę i albo segfaultuje albo zostaje zatrzymane przez ustawienia .ini.

Udało mi się wygrzebać, że problem jest nieskończona rekurencja w wierszu, który ładuje się $customerw \app\code\core\Mage\Customer\Helper\Data.php, getPasswordTimestamp().

$customer = Mage::getModel('customer/customer')
        ->setWebsiteId(Mage::app()->getStore()->getWebsiteId())
        ->load((int)$customerId);

Patrząc na ślad stosu nieskończonej rekurencji, ciągle zapętla się w to w kółko. Jakoś wydaje się, że ->load()ostatecznie wywołuje getPasswordTimestamp()metodę.

Obejście przedstawione w /magento//a/235984/67252 działa dobrze, ale chciałbym wiedzieć, co się dzieje.


0

Po zastosowaniu poprawki SUPEE 10752, Zarejestruj się, a kasa przeniesie stronę sukcesu na stronę główną. Jakieś sugestie?


-1

Po zastosowaniu SUPEE-10752 i kompilacji zobaczyliśmy pustą stronę w / checkout / *

wersja: 1.9.1.0

Warunki wyzwalania: zastosowanie SUPEE-10752 + włącz kompilator + zaloguj się jako klient, a następnie odwiedź / kasy / *

Tylko dla wyjaśnienia: Z dezaktywowanym kompilatorem wszystko poszło dobrze, z aktywowanym kompilatorem widzieliśmy tylko pustą stronę koszyka po zalogowaniu bez żadnych wpisów w dzienniku (nawet po aktywowaniu wszystkich możliwych dzienników i trybu programisty).

Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.