Что такое экранирование в программировании
Перейти к содержимому

Что такое экранирование в программировании

  • автор:

Экранирование, специальные символы

Как мы уже видели, обратная косая черта \ используется для обозначения классов символов, например \d . Это специальный символ в регулярных выражениях (как и в обычных строках).

Есть и другие специальные символы, которые имеют особое значение в регулярном выражении. Они используются для более сложных поисковых конструкций. Вот полный перечень этих символов: [ ] \ ^ $ . | ? * + ( ) .

Не надо пытаться запомнить этот список: мы разберёмся с каждым из них по отдельности, и таким образом вы выучите их «автоматически».

Экранирование символов

Допустим, мы хотим найти буквально точку. Не «любой символ», а именно точку.

Чтобы использовать специальный символ как обычный, добавьте к нему обратную косую черту: \. .

Это называется «экранирование символа».

alert( "Глава 5.1".match(/\d\.\d/) ); // 5.1 (совпадение!) alert( "Глава 511".match(/\d\.\d/) ); // null ("\." - ищет обычную точку)

Круглые скобки также являются специальными символами, поэтому, если нам нужно использовать именно их, нужно указать \( . В приведённом ниже примере ищется строка «g()» :

alert( "function g()".match(/g\(\)/) ); // "g()"

Если мы ищем обратную косую черту \ , это специальный символ как в обычных строках, так и в регулярных выражениях, поэтому мы должны удвоить её.

alert( "1\\2".match(/\\/) ); // '\'

Косая черта

Символ косой черты ‘/’ , так называемый «слэш», не является специальным символом, но в JavaScript он используется для открытия и закрытия регулярного выражения: /. шаблон. / , поэтому мы должны экранировать его.

Вот как выглядит поиск самой косой черты ‘/’ :

alert( "/".match(/\//) ); // '/'

С другой стороны, если мы не используем короткую запись /. / , а создаём регулярное выражение, используя new RegExp , тогда нам не нужно экранировать косую черту:

alert( "/".match(new RegExp("/")) ); // находит /

new RegExp

Если мы создаём регулярное выражение с помощью new RegExp , то нам не нужно учитывать / , но нужно другое экранирование.

Например, такой поиск не работает:

let regexp = new RegExp("\d\.\d"); alert( "Глава 5.1".match(regexp) ); // null

Аналогичный поиск в примере выше с /\d\.\d/ вполне работал, почему же не работает new RegExp(«\d\.\d») ?

Причина в том, что символы обратной косой черты «съедаются» строкой. Как вы помните, обычные строки имеют свои специальные символы, такие как \n , и для экранирования используется обратная косая черта.

Вот как воспринимается строка «\d.\d»:

alert("\d\.\d"); // d.d

Строковые кавычки «съедают» символы обратной косой черты для себя, например:

  • \n – становится символом перевода строки,
  • \u1234 – становится символом Юникода с указанным номером,
  • …А когда нет особого значения: как например для \d или \z , обратная косая черта просто удаляется.

Таким образом, new RegExp получает строку без обратной косой черты. Вот почему поиск не работает!

Чтобы исправить это, нам нужно удвоить обратную косую черту, потому что строковые кавычки превращают \\ в \ :

let regStr = "\\d\\.\\d"; alert(regStr); // \d\.\d (теперь правильно) let regexp = new RegExp(regStr); alert( "Глава 5.1".match(regexp) ); // 5.1

Итого

  • Для поиска специальных символов [ ] \ ^ $ . | ? * + ( ) , нам нужно добавить перед ними \ («экранировать их»).
  • Нам также нужно экранировать / , если мы используем /. / (но не new RegExp ).
  • При передаче строки в new RegExp нужно удваивать обратную косую черту: \\ для экранирования специальных символов, потому что строковые кавычки «съедят» одну черту.

Экранирование символов

Экранирование символов — замена в тексте управляющих символов на соответствующие текстовые подстановки.

Определение

Обычно языки программирования, текстовые командные интерфейсы, языки разметок текста (HTML, TEX, wiki) имеют дело со структурированным текстом, в котором некоторые символы (и их комбинации) используются в качестве управляющих, в том числе управляющих структурой текста. В ситуации, когда необходимо использовать такой символ в качестве «обычного символа языка», применяют экранирование.

Условно экранирование может быть разделено на три типа:

  • экранирование одиночного символа
  • экранирование группы символов с помощью последовательности символов «начать экранирование», «закончить экранирование»
  • с помощью командной последовательности «начать экранирование» и символа «конец экранирования», который задаётся до начала экранируемого текста.dnb_page

Отсутствие экранирования как причина уязвимости

Экранирование символов привлекает особое внимание, когда структурированный текст генерируется автоматически. Включение в текст произвольных строковых данных предполагает обязательное экранирование в них управляющих символов. В то же время, очень часто реальные строки таких символов не содержат, что позволяет программисту пропускать эту операцию совсем и получать более простую программу, корректно работающую с «любыми разумными» строковыми данными. Однако, такой упрощенный код имеет скрытую уязвимость, потому что стороннее лицо (автор строковых данных) получает несанкционированную возможность влиять на структуру генерируемого текста. Уязвимость становится серьёзной, если созданный текст является чьей-то программой. Традиционно таким проблемам подвержены системы, использующие языки SQL (см. SQL-injection) и HTML (см. Сross Site Sсriрting).

Примеры

Экранирование одиночного символа

  • В языке программирования Си, внутри строк экранирование символов осуществляется с помощью символа ‘\’, помещённого перед экранируемым символом. (При этом символ ‘\’ может экранировать себя, то есть для вывода бэкслеша используется комбинация ‘\\’), этот же символ используется для экранирования символов в командной строке unix.
  • В командной строке microsoft windows экранирование части символов осуществляется с помощью символа ‘^’, помещённого перед экранируемым символом.

Экранирование группы символов

  • В языке программирования python экранирование группы символов в строке осуществляется указанием буквы r (от англ.raw — необработанный) перед строкой, т. е. символы экранируются последовательностями экранируемый текст«
  • В вики-разметке экранирование текста осуществляется с помощью псевдотегов и . Если нужно записать сам псевдотег , это делается символами подстановки ( <nowiki> ).

О метке

Экранирование — способ размещения внутри литерала символов окончания литерала, а также непечатаемых и специальных символов. Метка для вопросов, связанных с проблемами экранирования символов в различных языках программирования, разметки и т. д.

Экранирование — способ размещения внутри литерала символа окончания литерала.

Классический пример использования экранирования — помещение в строковые литералы одиночных и двойных кавычек путем вставки символа \ (обратный слеш) перед экранируемым символом. Данный способ применяется в широком спектре языков программирования, в которых используется Си-подобный синтаксис (Си, Си++, Java, JavaScript, Perl, PHP и т. д.) Кроме того применение обратного слеша позволяет вставлять любые символы путем указания шестнадцатеричного или восьмеричного кода символа, например «\x5a» или «\0132» это экранированное представление символа z (в любой однобайтовой кодировке).

Кроме использования символа обратного слеша бывают и другие способы экранирования символа:

  • Повторение символа. Например: «»» — двойная кавычка» . Способ используется в языке Basic;
  • Сущности вида < , " , Ӓ , ᨫ и т. д. Используются в XML-подобных языках (в том числе HTML).

Проблемы с экранированием возникают чаще всего тогда, когда используются литералы различной природы (языка) вложенные друг в друга. Также бывают случаи, когда программист просто забывает что-либо экранировать. В последнем случае может помочь подсветка синтаксиса в редакторе.

Неправильное экранирование (или его отсутствие) может привести к следующим последствиям:

  • Ошибки на этапе компиляции и невозможность сборки программы;
  • Неправильное отображение результатов выполнения кода;
  • Нарушение верстки веб-страниц;
  • Возможность реализации SQL-инъекций для внесения несанкционированных изменений в базы данных;
  • Возможность внедрения вредоносного кода на веб-страницу;
  • Взлом веб-сайта.

C4: Кодирование и экранирование данных¶

Кодирование лучше всего применять непосредственно перед передачей данных интерпретатору. Если применить данный метод на слишком раннем этапе обработки запроса, то кодирование или экранирование может сказаться на использовании контента в других частях программы. Например, если перед сохранением в базе данных HTML-контент экранируется, а интерфейс автоматически экранирует эти данные еще раз, то содержимое не будет отображаться корректно из-за двойного экранирования.

Контекстное кодирование выходных данных¶

Контекстное кодирование выходных данных является ключевым для безопасного программирования и предотвращения межсайтового выполнения сценариев. Подобная мера защиты применяется при создании интерфейсов пользователя, непосредственно перед динамическим добавлением непроверенных данных к HTML-коду. Тип кодирования будет зависеть от места (или контекста) отображения или хранения данных в документе. Типы кодирования, рекомендуемые к использованию при создании безопасного интерфейса: кодирование сущностей или атрибутов HTML, а также кодирование JavaScript и URL.

Примеры кодирования на Java¶

Примеры использования кодировщика Java, обеспечивающего контекстное кодирование выходных данных, можно посмотреть на сайте проекта кодировщика Java от OWASP.

Примеры кодирования в .NET¶

Начиная с .NET 4.5, библиотека антимежсайтового выполнения сценариев является частью фреймворка, но не используется по умолчанию. Вы можете назначить AntiXssEncoder из этой библиотеки в качестве стандартного кодировщика вашего приложения, изменив настройки web.conf. При кодировании выходных данных необходимо учитывать контекст, т. е. использовать соответствующую функцию из библиотеки AntiXSSEncoder в зависимости от расположения данных в документе.

Примеры кодирования на PHP¶

Zend Framework 2¶

В Zend Framework 2 (ZF2) для кодирования выходных данных может быть использован ZendEscaper. Примеры контекстного кодирования можно посмотреть на странице, посвященной контекстному экранированию с помощью zend-escaper.

Другие способы кодирования и защиты от внедрений¶

Кодирование или экранирование может быть использовано для предотвращения других форм внедрений в контент. Например, можно нейтрализовывать некоторые специальные метасимволы при вводе данных для системных команд. Это называют «экранированием команд ОС», «экранированием shell» и т. п. Подобная защита может быть использована для предотвращения «Внедрения команд».

Существуют и другие формы экранирования, которые могут быть использованы для предотвращения внедрений, например, экранирование атрибутов XML, защищающее от различных форм внедрений XML и XML-путей, а также экранирование уникальных имен LDAP, позволяющее предотвратить различные LDAP-внедрения.

Нормализация и кодировка символов¶

Кодировка Юникод — это способ хранения символов с использованием нескольких байтов. При вводе данных злоумышленник может использовать Юникод, чтобы скрыть вредоносный код и получить возможность проведения различных атак. RFC 2279 описывает несколько способов кодировки текста.

Нормализация — это способ преобразования данных в простую или стандартную форму. В веб-приложениях нормализацию обычно используют для обеспечения единообразия символов всего контента при его хранении или отображении.

Защищенность от атак, связанных с нормализацией, означает отсутствие угроз безопасности приложения при вводе злоумышленником некорректно сформированных символов Юникода или любых других специально сформированных символов.

Предотвращаемые уязвимости¶

  • Топ-10 OWASP 2017 — A1: Внедрение
  • Топ-10 OWASP 2017 — А7: Межсайтовое выполнение сценариев (XSS)
  • Топ-10 OWASP 2014 (мобильные устройства) — M7: Внедрение на стороне клиента

Ссылки¶

  • Межсайтовое выполнение сценариев — общие сведения
  • Памятка OWASP: Предотвращение межсайтового выполнения сценариев (XSS) — предотвращение XSS в веб-приложениях
  • Памятка OWASP: Предотвращение межсайтового выполнения сценариев на основе объектной модели документа
  • Памятка OWASP: Предотвращение внедрений

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

Ваш адрес email не будет опубликован. Обязательные поля помечены *