Example #1
0
File: dns.c Project: jpoler/toxic
static int load_dns_domainlist(const char *path)
{
    FILE *fp = fopen(path, "r");

    if (fp == NULL)
        return -1;

    char line[MAX_DNS_LINE];

    while (fgets(line, sizeof(line), fp) && dns3_servers.lines < MAX_DNS_SERVERS) {
        int linelen = strlen(line);

        if (linelen < DNS3_KEY_SIZE * 2 + 5)
            continue;

        if (line[linelen - 1] == '\n')
            line[--linelen] = '\0';

        const char *name = strtok(line, " ");
        const char *keystr = strtok(NULL, " ");

        if (name == NULL || keystr == NULL)
            continue;

        if (strlen(keystr) != DNS3_KEY_SIZE * 2)
            continue;

        snprintf(dns3_servers.names[dns3_servers.lines], sizeof(dns3_servers.names[dns3_servers.lines]), "%s", name);
        int res = hex_string_to_bytes(dns3_servers.keys[dns3_servers.lines], DNS3_KEY_SIZE, keystr);

        if (res == -1)
            continue;

        ++dns3_servers.lines;
    }

    fclose(fp);

    if (dns3_servers.lines < 1)
        return -2;

    return 0;
}
Example #2
0
void QQ::pre_sign_in_step_1()
{
	int i = 0;
	unsigned char request [400];
	memset(request, 0, 400);
	unsigned char * msg_template;
	struct msg_t* tempmsg = NULL;
	hex_string_to_bytes("020e35003100040000000001", &msg_template);
	int* p = (int*) (msg_template + 7);
	*p = htonl(qq_id) ;

	memcpy((char*)request, msg_template, 12);
	delete[] msg_template;
	request[399] = (unsigned char) 0x03;

	for (i = 0; i < 5; i++)
	{
		try
		{
			tempmsg = new msg_t;
			tempmsg->msg = new unsigned char[400];
		}
		catch (bad_alloc & ba)
		{
			log_error(ba.what());
			return;
		}

		memcpy(tempmsg->msg, (char*)request, 400);
		tempmsg->len = 400;
		strcpy(tempmsg->ip,(char *) msgr->srv_ip[i]);
		tempmsg->port = msgr->srv_port;

		msgr->write_msg_queue(msgr->OUTGOING, tempmsg);
	}

	delay(200);
	set_state(QQ_WF_PREFIRST);
}
Example #3
0
void QQ::dispatch_msg()
{	
	uint8_t msg[messenger::BUF_SIZE] = {0};

	int len = 0;
	int i = 0;
	size_t j = 0;

	bool match = false;
	char msg_info[128] = {0};
	uint8_t* compare = NULL;
	size_t count = 0;

	qq_state_enum state = get_state();

	if (msgr == NULL || msgr->get_incoming_msg_queue_size() == 0)
	{
		return;
	}

	pthread_mutex_lock(&srv_ip_mtx);

	switch (state)
	{
	case QQ_WF_PREFIRST:
	case QQ_WF_REDIRECT:
		if (msgr->read_msg_queue(msgr->INCOMING, (char*)msg, this->srv_ip, this->srv_port, len) <= 0)
		{		
			break;
		}
		
		if (len < 10)
		{
			break;
		}

		// count = hex_string_to_bytes("02030000310004010003" , &compare);
		count = hex_string_to_bytes("02000000310004010003" , &compare); //2009-08-06		
		
		if (memcmp((char*)msg, compare, count) == 0)
		{
			delay(200);
			set_state(QQ_LOGINTOKEN);
		}

		delete[] compare;
		break;		

	case QQ_WF_LOGINTOKEN:
		if (msgr->read_msg_queue(msgr->INCOMING, (char*)msg, this->srv_ip, this->srv_port, len) <= 0)
		{		
			cout << "Read NONE!" << endl;
			break;
		}

		if (len >= 34)
		{
			// 请求登录令牌的命令号 0x0062
			count = hex_string_to_bytes("020e35006200000018", &compare); 
			match = true;

			for (j = 0; j < count; j++)
			{
				if (j == 5 || j == 6)
					continue;
				if (msg[j] != compare[j])
				{
					match = false;
					break;
				}
			}

			delete[] compare;
		}
		if (match)
		{
			pthread_mutex_lock(&login_token_mtx);
			for (j = 0; j < 24; j++)
				login_token[j] = msg[j + 9];	
			pthread_mutex_unlock(&login_token_mtx);
			delay(200);
			set_state(QQ_LOGIN_IN);
		}
		break;

	case QQ_WF_LOGIN_IN:
		{
			if (msgr->read_msg_queue(msgr->INCOMING, (char*)msg, this->srv_ip, this->srv_port, len) <= 0)
			{		
				break;
			}
			
			if (len < 32)
			{
				printf("QQ_WF_LOGIN_IN: len == %d < 32, break.\n", len);
				break;
			}
			count = hex_string_to_bytes("020e350022", &compare);

			if (memcmp((char*)msg, compare, count) != 0)
			{
				delete[] compare; 
				break;
			}
			delete[] compare; 			

			if (len == 32)
			{
				delay(200);
				set_state(QQ_REDIRECT);
				//cout << "QQ_REDIRECT" << endl;
				pthread_mutex_lock(&rand_key_mtx);
				TEA tea(rand_key);
				pthread_mutex_unlock(&rand_key_mtx);

				unsigned char * plain_msg = NULL;
				if (tea.qq_decrypt((msg + 7), 24, &plain_msg) != 11)
				{
					cout << "Decrypt Failed!" << endl;
					delay(200);
					set_state(QQ_ZERO);
					break;
				}
				unsigned int   n_ip = *((unsigned int *) (plain_msg + 5));
				unsigned short n_port = *((unsigned short *) (plain_msg + 9));
				unsigned short h_port = ntohs(n_port);
				unsigned int h_ip = ntohl(n_ip);

				memset(srv_ip, 0, IPADDR_LEN);
				sprintf(srv_ip, "%d.%d.%d.%d", 
					(h_ip >> 24) % 0x100,
					(h_ip >> 16) % 0x100, 
					(h_ip >> 8) % 0x100,
					h_ip % 0x100);

				srv_port = h_port;
				delete[] plain_msg;
				break;
			}

			if (len == 88)
			{
				printf("QQ_WF_LOGIN_IN: recieved 88 bytes.\n");	
			}

			if (len != 192)
			{
				printf("QQ_WF_LOGIN_IN: len == %d != 192, login failed, try again.\n", len);
				set_state(QQ_ZERO);
				break;
			}

			uint8_t * pwhash2 = NULL;
			hex_string_to_bytes(qq_pw, &pwhash2);		

			TEA tea(pwhash2);
			uint8_t * plain_msg = NULL;

			try
			{
				tea.qq_decrypt((msg + 7), 184, &plain_msg);
			}
			catch (out_of_range e)
			{
				cout << e.what() << endl;
			}

			uint32_t my_qq_id = 0;
			uint32_t my_ip = 0;
			uint16_t my_port = 0;
			uint32_t srv_listen_ip = 0;
			uint16_t srv_listen_port = 0;
			time_t login_time = 0;
			struct tm* tm_ptr;
			uint32_t unknown_ip = 0;

			switch (plain_msg[0])
			{
			case 0x00:
				memcpy(session_key, plain_msg + 1, 16);				
				delay(200);
				set_state(QQ_PRE_ONLINE_FIR);

				my_qq_id = ntohl(*((uint32_t *) (plain_msg + 17)));
				my_ip = ntohl(*((uint32_t *) (plain_msg + 21)));
				my_port = ntohs(*((uint16_t *) (plain_msg + 25)));
				srv_listen_ip = ntohl(*((uint32_t *) (plain_msg + 27)));
				srv_listen_port = ntohs(*((uint16_t *) (plain_msg + 31)));
				login_time = (time_t)
					ntohl(*((uint32_t *) (plain_msg + 33)));
				unknown_ip = ntohl(*((uint32_t *) (plain_msg + 63)));

				tm_ptr = localtime(&login_time);					

				sprintf(client_ip_port, "%d.%d.%d.%d:%d",
					(my_ip >> 24) % 0x100, (my_ip >> 16) % 0x100,
					(my_ip >> 8) % 0x100, my_ip % 0x100, my_port);		

				sprintf(signin_time, "%02d:%02d:%02d", tm_ptr->tm_hour,
					tm_ptr->tm_min, tm_ptr->tm_sec);

				sprintf(msg_info, "QQ ID:\t%d\r\nIP Addr:\t%s\r\nTime:\t\t%s",
					my_qq_id, client_ip_port, signin_time);
				log_event(msg_info);

				break;

			default:
				delay(200);
				set_state(QQ_ZERO);
				break;
			}

			delete[] plain_msg;	
			delete[] pwhash2;

			break;
		}

	case QQ_WF_PRE_ONLINE_FIR:
		{
			if (msgr->read_msg_queue(msgr->INCOMING, (char*)msg, this->srv_ip, this->srv_port, len) <= 0)
			{		
				break;
			}

			cout << "Server IP:\t" << srv_ip << ":" << srv_port << endl;

			if (msg[0] == 0x02 &&
				msg[1] == 0x0e &&
				msg[2] == 0x35)
			{
				TEA tea(session_key);
				unsigned char * plain_msg = NULL;
				tea.qq_decrypt((msg + 7), len - 8, &plain_msg);
				unsigned short order = msg[3] * 0x100 + msg[4];

				switch (order)
				{
				case 0x6:
					{
						my_profile_gotten = true;
						set_state(QQ_PRE_ONLINE_SEC);
						break;
					}
				}

				delete[] plain_msg;
			}

			break;
		}

	case QQ_WF_PRE_ONLINE_SEC:
		{
			if (msgr->read_msg_queue(msgr->INCOMING, (char*)msg, this->srv_ip, this->srv_port, len) <= 0)
			{		
				break;
			}

			if (msg[0] == 0x02 &&
				msg[1] == 0x0e &&
				msg[2] == 0x35)
			{
				TEA tea(session_key);
				unsigned char * plain_msg = NULL;
				int msg_len = tea.qq_decrypt((msg + 7), len - 8,
					&plain_msg);
				unsigned short order = msg[3] * 0x100 + msg[4];

				switch (order)
				{
				case 0x26:
					{
						memcpy(friend_id, plain_msg, 2);

						if (plain_msg[0] * 0x100 + plain_msg[1] == 0xffff)
						{
							set_state(QQ_ONLINE);							
							delay(200);
						}
						else
						{
							delay(200);
							set_state(QQ_PRE_ONLINE_SEC);
						}

						i = 2;

						while (i < msg_len)
						{
							int* pint = (int*) (plain_msg + i);
							int buddy_id = ntohl(*pint);
							unsigned char ssize = *(plain_msg + i + 8);
							char* nickname = new char[ssize + 1];
							memset(nickname, 0, ssize + 1);
							memcpy(nickname, plain_msg + i + 9, ssize);
							char ss[20];
							sprintf(ss, "<%d>", buddy_id);
							char* listchars = new char[ssize + 1 + 20];
							strcpy(listchars, nickname);
							strcat(listchars, ss);

							string buddy_nickname = nickname;
							contact.insert(pair<int, string>(buddy_id,
								buddy_nickname));

							delete[] nickname;
							delete[] listchars;
							i = i + 9 + ssize + 4;
						}

						break;
					}
				}

				delete[] plain_msg;
			}

			break;
		}

	case QQ_ONLINE:
		{
			if (msgr->read_msg_queue(msgr->INCOMING, (char*)msg, this->srv_ip, this->srv_port, len) <= 0)
			{		
				break;
			}
			if (msg[0] == 0x02)
			{
				TEA tea(session_key);
				unsigned char * plain_msg = NULL;
				int msg_len = tea.qq_decrypt((msg + 7), len - 8,
					&plain_msg);

				unsigned short order = msg[3] * 0x100 + msg[4];
				char signature[128];

				switch (order)
				{
				case 0x02:
					pthread_mutex_lock(&drop_flag_mtx);
					drop_flag = 0;
					pthread_mutex_unlock(&drop_flag_mtx);
					break;
	
				case 0x17:
					{
						int sender_qq = ntohl(*((int*) plain_msg));      //发送者QQ号	
						int mlong = msg_len - 65 - plain_msg[msg_len - 1];

						if (mlong > 0)
						{
							char* received_msg = new char[mlong + 1];
							memset(received_msg, 0, mlong + 1);
							memcpy(received_msg, plain_msg + 65, mlong);

							if (config.set_received_msg_as_personal_msg)
							{
								strncpy((char *) signature, received_msg, 100);
								set_personal_msg((const char *) signature);
							}

							process_msg(sender_qq, received_msg);

							delete[] received_msg;
							/*
							 * 回复 收到了消息
							 * 1. 消息发送者QQ号,4字节
							 * 2. 消息接收者QQ号,4字节,也就是我
							 * 3. 消息序号,4字节
							 * 4. 发送者IP,4字节
							 */
							unsigned char * plaintext = new unsigned char[16];
							memcpy(plaintext, plain_msg, 16);
							unsigned char * ciphertext = NULL;
			
							size_t miSize = tea.qq_encrypt(plaintext, 16,
								&ciphertext);

							size_t msg_size = miSize + 12;

							uint8_t* request = new_request(0x17, msg_size);

							request[5] = msg[5]; // TEA::Rand();
							request[6] = msg[6]; // TEA::Rand();
							memcpy(request + 11, ciphertext, miSize);

							push_msg(request, msg_size, false);
				
							delete[] plaintext;
							delete[] ciphertext;
							delete[] request;
						}
						break;
					}
				}
				delete [] plain_msg;
			}

			break;
		}

	default:
		break;
	}
Example #4
0
int main(int argc, char **argv) {
  int opt, k_flag = 0, p_flag = 0, d_flag = 0;
  uint8_t *in_block = NULL, *key = NULL;
  int keylen;                            // Key length in bits
  uint8_t n_k;                           // Key length in bytes
  uint8_t n_r;                           // Number of rounds
  uint8_t **key_schedule;

  // =======================
  // GET KEY LENGTH AS PARAM
  // =======================

  if (DEBUG) printf("INPUT\n");

  while ((opt = getopt (argc, argv, "dk:i:")) != -1) {
    int len_bits = 0;      // Length of hex string -> length of bits
    switch (opt) {
      case 'd':
        // Decrypt option
        d_flag = 1;
        break;

      case 'k':
        len_bits = strlen(optarg) / 2 * 8;
        // User option to specify key as hex string
        if (!(len_bits == 128 || len_bits == 192 || len_bits == 256))
          exit_with_usage_message();

        keylen = len_bits;
        key = hex_string_to_bytes(optarg);

        if (DEBUG) printf(" KeyLen: %d\n", keylen);
        debug_print_block(key, "  InKey: ");
        k_flag = 1;
        break;

      case 'i': // Input block (plaintext or ciphertext)
        len_bits = strlen(optarg) / 2 * 8;
        if (len_bits != 128)
          exit_with_usage_message();

        in_block = hex_string_to_bytes(optarg);
        p_flag = 1;
        break;

      default:
        printf (USAGE_MESSAGE);
        exit(0);
    }
  }

  if (!k_flag || !p_flag)
    exit_with_usage_message();

  // Compute number of rounds and keylen in bytes
  switch (keylen) {
    case 128:
      n_k = 4;      n_r = 10;
      break;
    case 192:
      n_k = 6;      n_r = 12;
      break;
    case 256:
      n_k = 8;      n_r = 14;
      break;
    default:
      printf("keylen is not 128/192/256.");
      exit(1);
  }

  key_schedule = key_expansion(key, n_k, n_r);

  if (d_flag)
    inv_cipher(in_block, key_schedule, n_k, n_r);
  else
    cipher(in_block, key_schedule, n_k, n_r);
}