hydra-teamspeak.c 4.23 KB
Newer Older
Mati's avatar
Mati committed
1
#include "hydra-mod.h"
2 3 4 5

#ifdef HAVE_ZLIB
#include <zlib.h>
#else
Mati's avatar
Mati committed
6
#include "crc32.h"
7
#endif
Mati's avatar
Mati committed
8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35

/*

This module brings support for Teamspeak version 2.x (TS2 protocol)
Tested with version 2.0.r23.b19, server uses to ban ip for 10 min
when bruteforce is detected.

TS1 protocol (tcp/8765) is not supported
TS3 protocol (udp/9987) is not needed as user/pass is not used anymore

*/

struct team_speak {
  char header[16];
  unsigned long crc;
  char clientlen;
  char client[29];
  char oslen;
  char os[29];
  char misc[10];
  char userlen;
  char user[29];
  char passlen;
  char pass[29];
  char loginlen;
  char login[29];
};

36
extern int32_t hydra_data_ready_timed(int32_t socket, long sec, long usec);
Mati's avatar
Mati committed
37 38 39 40

extern char *HYDRA_EXIT;
char *buf;

41
int32_t start_teamspeak(int32_t s, char *ip, int32_t port, unsigned char options, char *miscptr, FILE * fp) {
Mati's avatar
Mati committed
42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72
  char *empty = "";
  char *login, *pass;
  char buf[100];
  struct team_speak teamspeak;

  if (strlen(login = hydra_get_next_login()) == 0)
    login = empty;
  if (strlen(pass = hydra_get_next_password()) == 0)
    pass = empty;

  memset(&teamspeak, 0, sizeof(struct team_speak));

  memcpy(&teamspeak.header, "\xf4\xbe\x03\x00\x00\x00\x00\x00\x00\x00\x00\x00\x01\x00\x00\x00", 16);

  teamspeak.clientlen = 9;
  strcpy((char *) &teamspeak.client, "TeamSpeak");

  teamspeak.oslen = 11;
  strcpy((char *) &teamspeak.os, "Linux 2.6.9");

  memcpy(&teamspeak.misc, "\x02\x00\x00\x00\x20\x00\x3c\x00\x01\x02", 10);

  teamspeak.userlen = strlen(login);
  strncpy((char *) &teamspeak.user, login, 29);

  teamspeak.passlen = strlen(pass);
  strncpy((char *) &teamspeak.pass, pass, 29);

  teamspeak.loginlen = 0;
  strcpy((char *) &teamspeak.login, "");

73 74 75
#ifdef HAVE_ZLIB
  teamspeak.crc = crc32(0L, (const Bytef *)&teamspeak, sizeof(struct team_speak));
#else
Mati's avatar
Mati committed
76
  teamspeak.crc = crc32(&teamspeak, sizeof(struct team_speak));
77
#endif
Mati's avatar
Mati committed
78 79 80 81 82 83 84 85 86 87 88

  if (hydra_send(s, (char *) &teamspeak, sizeof(struct team_speak), 0) < 0) {
    return 3;
  }

  if (hydra_data_ready_timed(s, 5, 0) > 0) {
    hydra_recv(s, (char *) buf, sizeof(buf));
    if (buf[0x58] == 1) {
      hydra_report_found_host(port, ip, "teamspeak", fp);
      hydra_completed_pair_found();
    }
89
    if (buf[0x4B] != 0) {
90
      hydra_report(stderr, "[ERROR] Child with pid %d terminating, can not connect\n", (int32_t) getpid());
91 92 93
      hydra_child_exit(1);
    }
  } else {
94
    hydra_report(stderr, "[ERROR] Child with pid %d terminating, can not connect\n", (int32_t) getpid());
95
    hydra_child_exit(1);
Mati's avatar
Mati committed
96 97 98 99 100 101 102 103 104
  }

  hydra_completed_pair();
  if (memcmp(hydra_get_next_pair(), &HYDRA_EXIT, sizeof(HYDRA_EXIT)) == 0)
    return 3;

  return 1;
}

105 106 107
void service_teamspeak(char *ip, int32_t sp, unsigned char options, char *miscptr, FILE * fp, int32_t port, char *hostname) {
  int32_t run = 1, next_run = 1, sock = -1;
  int32_t myport = PORT_TEAMSPEAK;
Mati's avatar
Mati committed
108 109 110 111 112 113 114 115 116 117 118

  hydra_register_socket(sp);

  if (memcmp(hydra_get_next_pair(), &HYDRA_EXIT, sizeof(HYDRA_EXIT)) == 0)
    run = 3;

  while (1) {
    switch (run) {
    case 1:                    /* connect and service init function */
//      if (sock >= 0)
//      sock = hydra_disconnect(sock);
119
//      usleepn(300);
Mati's avatar
Mati committed
120 121 122 123 124 125
      if (sock < 0) {
        if (port != 0)
          myport = port;
        sock = hydra_connect_udp(ip, myport);
        port = myport;
        if (sock < 0) {
126
          hydra_report(stderr, "[ERROR] Child with pid %d terminating, can not connect\n", (int32_t) getpid());
Mati's avatar
Mati committed
127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144
          hydra_child_exit(1);
        }
      }
      next_run = start_teamspeak(sock, ip, port, options, miscptr, fp);
      break;
    case 3:                    /* clean exit */
      if (sock >= 0)
        sock = hydra_disconnect(sock);
      hydra_child_exit(2);
      return;
    default:
      hydra_report(stderr, "[ERROR] Caught unknown return code, exiting!\n");
      hydra_child_exit(2);
    }
    run = next_run;
  }
}

145
int32_t service_teamspeak_init(char *ip, int32_t sp, unsigned char options, char *miscptr, FILE * fp, int32_t port, char *hostname) {
Mati's avatar
Mati committed
146 147 148 149 150 151 152 153 154 155 156 157
  // 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

  return 0;
}