<style>
.reveal {
font-size: 36px;
}
</style>
# Secure Web Applications Development
## SQL Security
---
Вопросы по заданиям?
---
## Темы занятия
* Права доступа в SQL
* Принципы SQL injection hardening
* Проблема состояния гонки
* Защита на основе SQL
---
## Права доступа в SQL
Современные СУБД позволяют очень гибко настраивать права доступа.
Права могут быть разграничены к:
- схемам;
- хранимым процедурам;
- таблицам;
- колонкам;
- и даже к отдельным записям;
---
## Права доступа в SQL
- [MySQL](https://dev.mysql.com/doc/refman/8.0/en/grant.html)
- [PostgreSQL](https://postgrespro.ru/docs/postgresql/13/sql-grant)
- [MSSQL](https://docs.microsoft.com/en-us/sql/t-sql/statements/grant-object-permissions-transact-sql?view=sql-server-ver15)
---
## Права доступа к схемам
```sql
GRANT ALL PRIVILEGES ON database_name.* TO 'username'@'localhost';
```
---
## Разграничение типа доступа
Можно разграничить уровень доступа:
- GRANT SELECT
- GRANT UPDATE
- GRANT INSERT
- GRANT DELETE
---
## Права доступа к колонкам
```sql
GRANT SELECT(email) ON `database`.`table` TO user;
```
---
## Хранимые процедуры
Разрешение на вызов процедур:
```sql
GRANT EXECUTE ON `test`.`procedure_name` TO mysql_user;
```
---
## Выполнение хранимых процедур с правами создателя
Также можно реализовать вызов процедур с правами создателя процедуры:
```sql
CREATE DEFINER = 'root'@'localhost' PROCEDURE
get_data_from_secret_table (IN in_data VARCHAR(300),
OUT res VARCHAR(300))
BEGIN
SELECT data INTO res FROM secret_table WHERE data=in_data;
END //
```
---
## Выполнение хранимых процедур с правами создателя
Далее мы даем права на выполнение этой процедуры и пользователь может получать данные из `secret_table` даже если у него нет никаких прав на доступ к этой таблице
```sql
GRANT EXECUTE ON `test`.`get_data_from_secret_table` TO mysql_user;
```
```sql
CALL get_data_from_secret_table('test',@result);
SELECT @result;
```
---
## VIEW для разграничения доступа к row
Аналогичная идея может быть использована для разграничения доступа к row. Тут `VIEW` "выполняется" от создателя с помощью `SQL SECURITY DEFINER`
```sql
CREATE
OR REPLACE SQL SECURITY DEFINER
VIEW `data_1` AS
SELECT * FROM `data` WHERE (`data`.`id` = '1');
GRANT SELECT,UPDATE ON example.data_1 TO mysql_user;
```
---
## Задание на SQL Hardening
---
## Race condition
---
## Race condition
### Состояние гонки
Проблема многопоточных приложений, при которой конечный результат зависит от того, в каком порядке потоки получат управление.
---
## Race condition
Пример с переводом денег
---

---

---

---

---

---

---

---

---
## Race condition
Способ защиты - синхронизация. Один поток "захватывает" (acquire) объект синхронизации. Пока он не "отпущен" (release), другие потоки не могут обращаться к защищаемым ресурсам.
---
## Race condition
Синхронизация может быть выполнена:
- программно;
- на уровне сессий;
- на уровне БД;
---
## Race condition
Синхронизация на уровне БД.
Используются транзакции и конструкции `FOR SHARE`, `FOR UPDATE` и другие .
```sql=
SET autocommit=0;
SELECT column FROM table
WHERE id=333
FOR UPDATE;
UPDATE table SET column='xxx'
WHERE id=333;
COMMIT;
```
<Демонстрация в консоли>
---
## Race condition
Встречается также в других случаях, например, при проверке одноразовых паролей OTP.
---
## Race condition
Для одновременной отправки запросов можно также использовать плагин Burp `Turbo Intruder`:
https://portswigger.net/research/turbo-intruder-embracing-the-billion-request-attack
Скрипт:
https://github.com/PortSwigger/turbo-intruder/blob/master/resources/examples/race.py
---
## Race condition
Пример реальной накрутки бонусов в Starbucks:
https://habr.com/ru/post/258449/
---
## Задание на Race Condition
---
{"metaMigratedAt":"2023-06-16T11:43:51.615Z","metaMigratedFrom":"YAML","title":"SecChamps - 0x05 - SQL Security","breaks":true,"slideOptions":"{\"transition\":\"fade\",\"parallaxBackgroundImage\":\"https://i.imgur.com/YClZ1aY.jpg\"}","contributors":"[{\"id\":\"74341f14-c8ac-49ac-b077-53e0eec889fc\",\"add\":4647,\"del\":260}]"}