1. PHP / Говнокод #2664

    +163.3

    1. 1
    2. 2
    3. 3
    4. 4
    5. 5
    6. 6
    $udate = mktime(
      0,0,0,
      $_REQUEST["udate"][3] . $_REQUEST["udate"][4],
      $_REQUEST["udate"][0] . $_REQUEST["udate"][1],
      $_REQUEST["udate"][6] . $_REQUEST["udate"][7] . $_REQUEST["udate"][8] . $_REQUEST["udate"][9]
    );

    Продолжение феерической истории о том, как один мальчег не знал регулярок. Да что там регулярок...

    Запостил: Johnny, 25 Февраля 2010

    Комментарии (20) RSS

    • 1) как меньше писать
      $u = $_REQUEST["udate"]; // mm.dd.yyy
      $udate = mktime( 0,0,0, $u[3] .$u[4], $u[0].$u[1], $u[6].$u[7].$u[8].$u[9] );

      2) как нормально писать
      если у него дата уже задана в виде mm.dd.yyy, зачем вообще нужна mktime ???
      $udate = strtotime($_REQUEST[udate]);

      3) автору, зачем тут регулярки, но пример бредового кода налицо... +1 ???
      Ответить
      • я бы не стал доверять все ф-и strtotime... к тому же регуляркой можно одновременно проверить корректность формата (mm.dd.yyyy) и вычленить день месяц и год для mktime.
        Ответить
        • если юзверь введёт 32.13.8888 то mktime это кстати, прохавает, и просчитает по своемому... (причём 33.01.2000 >> 02.02.2000). зачем делать ненужные проверки регуляркой??? признак високосности года или 32 дня в году тоже там будете проверять???
          Ответить
          • хотя-бы затем, что поведение этой ф-и четко не документировано. "просчитает по своемому" это как?
            Ответить
            • Первым параметром функции должна быть строка с датой на английском языке, которая будет преобразована в метку времени относительно метки времени, переданной в now, или текущего времени, если аргумент now опущен. В случае ошибки возвращается false.

              $timestamp = strtotime($str);
              if ($timestamp===false)
              echo "Строка ($str) недопустима";
              Ответить
              • Клева! и чо дальше? Доки и я читать умею = )
                Ответить
                • А в чём тогда недокументированность???
                  Ответить
                  • полный список форматов дат, которые она хавает. плюс описание ее поведения, при подаче на вход некорректных дат. в одном случае она возращает значит false, а в другом пытается что-то накреативить и высрать осмысленный результат. Вон чо пишут: "The function expects to be given a string containing a US English date format and will try to parse that format into a Unix timestamp" Вилл трай... Незнаю, дело хозяйское, но в таких делах предпочитаю изобрести небольшой велосипед, чем использовать волшебные функции.
                    Ответить
        • регулярки? это хорошо) особенно хорошо когда:
          preg_replace() с /e
          ereg и null-байт
          Ответить
          • а, че?
            Ответить
            • Товарищ намекает на способ взлома через регулярки. Правда, в данном случае даже если и использовать регулярки для валидации, то уж подставлять внутрь регулярок пользовательский ввод стопудово на фиг не потребуется, так что взломом через регулярки тут не пахнет. Остаётся только согласиться: а, чё?
              Ответить
              • Как много нам открытий чудных... *ПОГНАЛ ГУГЛИТЬ*
                Ответить
              • трололо
                в $_REQUEST уже нельзя засунуть специально сформированные данные ?
                Ответить
                • вот и я про то же
                  Ответить
                • Товарищи, за чем дело-то стало, давайте прояснять.
                  preg_match('/регулярка/', $_REQUEST['anything'], $matches);

                  Лично я - о том, что в таком случае взлом исключён, потому что регулярка задана хардкодом, и в неё из реквеста ничего не валится. Ибо я категорически затрудняюсь представить, каким боком при валидации даты может потребоваться динамически формировать регулярку, да ещё и из пользовательского ввода. Ваше слово?
                  Ответить
                  • Собственно в данном случае ничо через регулярку и неломаемо. А мне от пользователя xXx_totalwar хотелось бы услышать подробности про "ereg и null-байт". Это че за уязвимость?
                    Ответить
                    • допустим есть такая вещь
                      if (ereg('/|(\.\.)', $_GET['page'])) die('error');
                      else include(trim($_GET['page']).'.html');

                      теперь запускаем скрипт script.php?page=%00../../../../etc/passwd%00a
                      Ответить
                    • Вообще говоря, я в посте выше накосячил, потому что взлом возможен только при использовании preg_replace, ибо только эта функция поддерживает ключ /e. Но к сути. Вот пример из доки к этой функции:
                      preg_replace("/(<\/?)(\w+)([^>]*>)/e", 
                                   "'\\1'.strtoupper('\\2').'\\3'", 
                                   $html_body);

                      При использовании модификатора /e на конце регулярки второй аргумент функции интерпретируется как PHP-код, в котором \nnn заменяются на соответствующие совпадения. А теперь представим, что регулярка каким-то образом формируется из пользовательского ввода, а magic_quotes=off. В этом случае юзер может написать: блаблабла/e%00, где %00 - нуль-байт. Функция preg_replace проигнорит остаток строки, идущий после нуль-байта. В результате получим в корне изменившееся поведение регулярки - она теперь эвалит второй аргумент. Ну а дальше ловкость рук, суть которой в том, чтобы заставить регэксп отэвалить то, что нам надо. Недавно читал список уязвимостей phpBB ранних версий - так там очень много дыр завязано как раз на этой штуке.

                      Про ereg() не знаю, принципиально им не пользуюсь, ибо медленный и deprecated.
                      Ответить
                      • Спасибо за разъяснение. Помню когда-то читал про это не не придал значения.
                        Ответить
                  • вообще то переполнение буфера в PCRE еще не отменяли
                    Ответить

    Добавить комментарий