/* This module is using freerdp3 lib Tested on: - Windows 7 pro SP1 - Windows 10 pro build 1809 - Windows Server 2016 build 1607 */ #include "hydra-mod.h" extern hydra_option hydra_options; extern char *HYDRA_EXIT; #ifndef LIBFREERDP void dummy_rdp() { printf("\n"); } #else #include #include freerdp *instance = 0; BOOL rdp_connect(char *server, int32_t port, char *domain, char *login, char *password) { int32_t err = 0; rdpSettings* settings = instance->context->settings; settings->Username = login; settings->Password = password; settings->IgnoreCertificate = TRUE; if (password[0] == 0) settings->AuthenticationOnly = FALSE; else settings->AuthenticationOnly = TRUE; settings->ServerHostname = server; settings->ServerPort = port; settings->Domain = domain; #if FREERDP_VERSION_MAJOR == 2 settings->MaxTimeInCheckLoop = 100; #endif // freerdp timeout format is microseconds -> default:15000 settings->TcpConnectTimeout = hydra_options.waittime * 1000; settings->TlsSecLevel = 0; freerdp_connect(instance); err = freerdp_get_last_error(instance->context); return err; } /* Client program */ int32_t start_rdp(char *ip, int32_t port, unsigned char options, char *miscptr, FILE *fp) { char *empty = ""; char *login, *pass; char server[64]; char domain[256]; int32_t login_result = 0; memset(domain, 0, sizeof(domain)); if (strlen(login = hydra_get_next_login()) == 0) login = empty; if (strlen(pass = hydra_get_next_password()) == 0) pass = empty; strncpy(server, hydra_address2string(ip), sizeof(server) - 1); if ((miscptr != NULL) && (strlen(miscptr) > 0)) { strncpy(domain, miscptr, sizeof(domain) - 1); domain[sizeof(domain) - 1] = 0; } login_result = rdp_connect(server, port, domain, login, pass); if (debug) hydra_report(stderr, "[DEBUG] rdp reported %08x\n", login_result); switch (login_result) { case 0: // login success hydra_report_found_host(port, ip, "rdp", fp); hydra_completed_pair_found(); break; case 0x00020009: case 0x00020014: case 0x00020015: // login failure hydra_completed_pair(); break; case 0x0002000f: // login failure hydra_completed_pair_skip(); break; case 0x0002000d: hydra_report(stderr, "[%d][rdp] account on %s might be valid but account not " "active for remote desktop: login: %s password: %s, " "continuing attacking the account.\n", port, hydra_address2string_beautiful(ip), login, pass); hydra_completed_pair(); break; case 0x00020006: case 0x00020008: case 0x0002000c: // cannot establish rdp connection, either the port is not opened or it's // not rdp return 3; default: if (verbose) { hydra_report(stderr, "[ERROR] freerdp: %s (0x%.8x)\n", freerdp_get_last_error_string(login_result), login_result); } return login_result; } if (memcmp(hydra_get_next_pair(), &HYDRA_EXIT, sizeof(HYDRA_EXIT)) == 0) return 2; return 1; } void service_rdp(char *ip, int32_t sp, unsigned char options, char *miscptr, FILE *fp, int32_t port, char *hostname) { int32_t run = 1, next_run = 1; int32_t myport = PORT_RDP; int32_t __first_rdp_connect = 1; if (port != 0) myport = port; hydra_register_socket(sp); if (memcmp(hydra_get_next_pair(), &HYDRA_EXIT, sizeof(HYDRA_EXIT)) == 0) return; while (1) { next_run = 0; switch (run) { case 1: /* run the cracking function */ if (__first_rdp_connect != 0) __first_rdp_connect = 0; else sleep(hydra_options.conwait); next_run = start_rdp(ip, myport, options, miscptr, fp); if (next_run == 1 && hydra_options.conwait) sleep(hydra_options.conwait); break; case 2: /* clean exit */ freerdp_disconnect(instance); freerdp_free(instance); hydra_child_exit(0); return; case 3: /* connection error case */ hydra_report(stderr, "[ERROR] freerdp: %s\n", "The connection failed to establish."); freerdp_free(instance); hydra_child_exit(1); return; default: hydra_child_exit(2); } run = next_run; } } int32_t service_rdp_init(char *ip, int32_t sp, unsigned char options, char *miscptr, FILE *fp, int32_t port, char *hostname) { // called before the childrens are forked off, so this is the function // which should be filled if initial connections and service setup has to be // performed once only. // // fill if needed. // // return codes: // 0 all OK // -1 error, hydra will exit, so print a good error message here // Disable freerdp output wLog *root = WLog_GetRoot(); WLog_SetStringLogLevel(root, "OFF"); // Init freerdp instance instance = freerdp_new(); if (instance == NULL || freerdp_context_new(instance) == FALSE) { hydra_report(stderr, "[ERROR] freerdp init failed\n"); return -1; } return 0; } void usage_rdp(const char *service) { printf("Module rdp is optionally taking the windows domain name.\n" "For example:\nhydra rdp://192.168.0.1/firstdomainname -l john -p " "doe\n\n"); } #endif