Finished SQL Injection assignment.
This commit is contained in:
parent
f186d5f7cc
commit
83a7bb6257
Binary file not shown.
@ -18,16 +18,76 @@ Es un ataque común en sistemas web que hacen uso de una base de datos, y
|
||||
especialmente cuando permiten interacción (indirecta) entre el usuario y la base
|
||||
de datos (e.g.\ formularios de entrada).
|
||||
|
||||
\section{Implementación}
|
||||
\subsection{Peticiones SQL Erróneas}
|
||||
\section{Peticiones SQL Erróneas}
|
||||
Cuando se escribe una petición SQL, se hace combinando en una misma sentencia
|
||||
los datos y los comandos.
|
||||
los datos y los comandos. A menudo, cuando se crean aplicaciones que interactuan
|
||||
con una base de datos, las entradas de los formularios se insertan
|
||||
\textit{verbatim} en la petición SQL. Cuando ocurre esto, un mal actor puede
|
||||
aprovecharse para inyectar un carácter de escape, y luego correr los comandos
|
||||
que quiera (i.e.\ ejecución de código arbitrario).
|
||||
|
||||
\subsection{Inyección SQL Ciega}
|
||||
\subsection{Inyección SQL De Segundo Orden}
|
||||
Por ejemplo, imaginemos un comando SQL que busque si existe un determinado
|
||||
usuario (asumimos que \texttt{PASSWD()} hace el \textit{hash}):
|
||||
|
||||
\section{Consecuencias}
|
||||
\begin{verbatim}
|
||||
SELECT * FROM Users WHERE
|
||||
username="nortega" AND password=PASSWD("MyPasswd");
|
||||
\end{verbatim}
|
||||
|
||||
\section{Soluciones}
|
||||
Esto, normalmente sólo escogería la entrada del usuario \textit{nortega}, y sus
|
||||
datos. Mas, si uno quisiera conseguir todos los datos de todos los usuarios,
|
||||
podría insertar en el formulario de usuario: \texttt{nortega"\ OR 1=1; --}. Al
|
||||
hacer esto, el comando terminaría siendo:
|
||||
|
||||
\begin{verbatim}
|
||||
SELECT * FROM Users WHERE
|
||||
username="nortega" OR 1=1;
|
||||
-- AND password=PASSWD("MyPasswd");
|
||||
\end{verbatim}
|
||||
|
||||
Por lo tanto, la contraseña quedaría ignorada (como comentario), y como la
|
||||
condición \texttt{1=1} siempre es verdad, terminaría por devolver todas las
|
||||
entradas de la tabla \texttt{Users}.
|
||||
|
||||
Para evitar esto, se pueden user ciertas funciones en lenguajes como PHP (e.g.
|
||||
\texttt{mysqli\_escape\_string()}) para \textit{escapar} aquellos caracteres que
|
||||
puedan usarse para hacer este tipo de inyecciones (e.g.\ añadiendo un
|
||||
\texttt{\textbackslash} antes del carácter para escapar el \textit{string}).
|
||||
Entonces el comando pasaría a ser lo siguiente:
|
||||
|
||||
\begin{verbatim}
|
||||
SELECT * FROM Users WHERE
|
||||
username="nortega\" OR 1=1; --"
|
||||
AND password=PASSWD("MyPasswd");
|
||||
\end{verbatim}
|
||||
|
||||
\section{Inyección SQL Ciega}
|
||||
Similarmente al caso anterior, la inyección ciega ocurre cuando la página o
|
||||
aplicación no muestra directamente la información de la base de datos, pero sí
|
||||
se mostraría de manera diferente cuando se cumple una condición. Por ejemplo,
|
||||
con el mismo código del caso anterior, si suponemos que el código se ejecuta en
|
||||
un formulario de \textit{login}, si el número de entradas es igual a 1, entonces
|
||||
acepta entrada en la cuenta. En cuyo caso, con añadir la condición
|
||||
\texttt{LIMIT 1}, ya entraría en la primera cuenta que encuentra (que
|
||||
normalmente es la cuenta del administrador).
|
||||
|
||||
\begin{verbatim}
|
||||
SELECT * FROM Users WHERE
|
||||
username="nortega" OR 1=1 LIMIT 1;
|
||||
-- AND password=PASSWD("MyPasswd");
|
||||
\end{verbatim}
|
||||
|
||||
Esto se evita de la misma manera que en la sección anterior.
|
||||
|
||||
\section{Inyección SQL De Segundo Orden}
|
||||
Supongamos que todos los formularios vienen con salvaguardas para evitar las
|
||||
inyecciones SQL. Aún así, es posible implementar un ataque más sutil que no
|
||||
afecte inmediatamente la base de datos, sino que lo afecte luego. En estos
|
||||
casos, la SQL del formulario se ejecuta correctamente, guardando el código SQL
|
||||
inyectado apropiadamente como un dato, para que luego sea usado y ejecutado
|
||||
erróneamente como código SQL. De este modo, podríamos decir que los casos
|
||||
anteriores eran inyecciones de primer nivel, ya que se ejecutaban inmediatamente
|
||||
del formulario, mientras que las inyecciones de segundo nivel son aquellos que
|
||||
se ejecutarán más tarde.
|
||||
|
||||
\end{document}
|
||||
|
Loading…
Reference in New Issue
Block a user