Example #1
0
File: list.c Project: LuaDist/cd
TList *cgm_AddList ( TList *l, int n, void *info )
{
 int i;

 if ( l == NULL)
   return NULL;

 if ( n < 1)
  n=1;

 if ( n > list_n(l) )
   return cgm_AppendList( l, info );

 --n;           /* o usuario ve a lista iniciando em 1 e a */
                /* lista e' implementada iniciando em 0     */

 if (list_n(l) == list_nba(l))
 {
  list_nba(l) *= 2;
  list_head(l) = (void **)realloc(list_head(l),list_nba(l)*sizeof(void*));
 }

 for (i=list_n(l)-1; i>=n; --i)
   list_head(l)[i+1]=list_head(l)[i];

 list_head(l)[n]=info;
 list_n(l)++;
 return l;
}
Example #2
0
File: list.c Project: LuaDist/cd
void *cgm_GetList ( TList *l, int n )
{
 if ( l == NULL || n <= 0)
   return NULL;

 return n > list_n(l) ? NULL : list_head(l)[n-1];
}
Example #3
0
File: list.c Project: LuaDist/cd
TList *cgm_AppendList ( TList *l, void *i )
{
 if ( l == NULL )
   return NULL;

 if (list_n(l) == list_nba(l))
 {
  list_nba(l) += 32;
  list_head(l) = (void **)realloc(list_head(l),list_nba(l)*sizeof(void*));
 }

 list_head(l)[list_n(l)]=i;
 list_n(l)++;

 return l;
}
Example #4
0
File: list.c Project: LuaDist/cd
int cgm_DelEntry ( TList *l, void *entry )
{
 int i=1;

 if ( l == NULL || list_n(l) == 0)
   return 0;

 for (i=0; i< list_n(l); ++i)
  if (list_head(l)[i]==entry)
  {
   cgm_DelList(l,i+1);              /* o usuario ve a lista iniciando em 1 e a */
                                /* lista e' implementada iniciando em 0     */
   return i+1;
  }
 return 0;
}
Example #5
0
void stack_for_each(list *stack, visit_fn visit) {
    list *p = stack;

    while (p != NULL) {
        visit(list_v(p));
        p = list_n(p);
    }
}
Example #6
0
list* stack_pop(list *stack) {
    list *obj;

    assert(stack != NULL);
    obj = list_n(stack);
    free(stack);
    return obj;
}
Example #7
0
list* stack_push(list *stack, object **v) {
    list *obj;

    obj = alloc_stack_node();
    list_v(obj) = v;
    list_n(obj) = stack;

    return obj;
}
Example #8
0
void stack_dispose(list *stack) {
    list *rest;

    while (stack != NULL) {
        rest = list_n(stack);
        free(stack);
        stack = rest;
    }
}
Example #9
0
File: list.c Project: LuaDist/cd
TList *cgm_NewList ( void )
{
 TList *l = (TList *) malloc ( sizeof (TList) );

 list_nba(l) = 8;
 list_head(l) = (void **)malloc(list_nba(l)*sizeof(void*));
 list_n(l) = 0;

 return l;
}
Example #10
0
File: list.c Project: LuaDist/cd
TList *cgm_DelList ( TList *l, int n )
{
 int i;

 if ( l == NULL || list_n(l) == 0 || n < 0)
   return NULL;

 if ( n < 1)
  n=1;

 if ( n > list_n(l))
  n=list_n(l);

 --n;           /* o usuario ve a lista iniciando em 1 e a */
                /* lista e' implementada iniciando em 0     */
 list_n(l)--;

 for (i=n; i<list_n(l); ++i)
   list_head(l)[i]=list_head(l)[i+1];

 return l;
}
Example #11
0
static void
rcv_task_login (struct htlc_conn *htlc, void *secure)
{
	char abuf[HOSTLEN+1];
	u_int32_t uid;
	u_int16_t icon16;
#ifdef CONFIG_HOPE
	u_int16_t hc;
	u_int8_t *p, *mal = 0;
	u_int16_t mal_len = 0;
	u_int16_t sklen = 0, macalglen = 0, secure_login = 0, secure_password = 0;
	u_int8_t password_mac[20];
	u_int8_t login[32];
	u_int16_t llen, pmaclen;
#ifdef CONFIG_CIPHER
	u_int8_t *s_cipher_al = 0, *c_cipher_al = 0;
	u_int16_t s_cipher_al_len = 0, c_cipher_al_len = 0;
	u_int8_t s_cipheralg[32], c_cipheralg[32];
	u_int16_t s_cipheralglen = 0, c_cipheralglen = 0;
	u_int8_t cipheralglist[64];
	u_int16_t cipheralglistlen;
#endif
#ifdef CONFIG_COMPRESS
	u_int8_t *s_compress_al = 0, *c_compress_al = 0;
	u_int16_t s_compress_al_len = 0, c_compress_al_len = 0;
	u_int8_t s_compressalg[32], c_compressalg[32];
	u_int16_t s_compressalglen = 0, c_compressalglen = 0;
	u_int8_t compressalglist[64];
	u_int16_t compressalglistlen;
#endif

	if (secure) {
		dh_start(htlc)
			switch (dh_type) {
				case HTLS_DATA_LOGIN:
					if (dh_len && dh_len == strlen(htlc->macalg) && !memcmp(htlc->macalg, dh_data, dh_len))
						secure_login = 1;
					break;
				case HTLS_DATA_PASSWORD:
					if (dh_len && dh_len == strlen(htlc->macalg) && !memcmp(htlc->macalg, dh_data, dh_len))
						secure_password = 1;
					break;
				case HTLS_DATA_MAC_ALG:
					mal_len = dh_len;
					mal = dh_data;
					break;
#ifdef CONFIG_CIPHER
				case HTLS_DATA_CIPHER_ALG:
					s_cipher_al_len = dh_len;
					s_cipher_al = dh_data;
					break;
				case HTLC_DATA_CIPHER_ALG:
					c_cipher_al_len = dh_len;
					c_cipher_al = dh_data;
					break;
				case HTLS_DATA_CIPHER_MODE:
					break;
				case HTLC_DATA_CIPHER_MODE:
					break;
				case HTLS_DATA_CIPHER_IVEC:
					break;
				case HTLC_DATA_CIPHER_IVEC:
					break;
#endif
#if defined(CONFIG_COMPRESS)
				case HTLS_DATA_COMPRESS_ALG:
					s_compress_al_len = dh_len;
					s_compress_al = dh_data;
					break;
				case HTLC_DATA_COMPRESS_ALG:
					c_compress_al_len = dh_len;
					c_compress_al = dh_data;
					break;
#endif
				case HTLS_DATA_CHECKSUM_ALG:
					break;
				case HTLC_DATA_CHECKSUM_ALG:
					break;
				case HTLS_DATA_SESSIONKEY:
					sklen = dh_len > sizeof(htlc->sessionkey) ? sizeof(htlc->sessionkey) : dh_len;
					memcpy(htlc->sessionkey, dh_data, sklen);
					htlc->sklen = sklen;
					break;
			}
		dh_end()

		if (!mal_len) {
no_mal:			hx_printf_prefix(htlc, 0, INFOPREFIX, "No macalg from server\n");
			hx_htlc_close(htlc);
			memset(htlc->password, 0, sizeof(htlc->password));
			return;
		}

		p = list_n(mal, mal_len, 0);
		if (!p || !*p)
			goto no_mal;
		macalglen = *p >= sizeof(htlc->macalg) ? sizeof(htlc->macalg)-1 : *p;
		memcpy(htlc->macalg, p+1, macalglen);
		htlc->macalg[macalglen] = 0;

		if (sklen < 32) {
			hx_printf_prefix(htlc, 0, INFOPREFIX,
					 "sessionkey length (%u) not big enough\n", sklen);
			hx_htlc_close(htlc);
			memset(htlc->password, 0, sizeof(htlc->password));
			return;
		}
#ifdef CONFIG_IPV6
		if (memcmp(htlc->sessionkey, &htlc->sockaddr.SIN_ADDR.S_ADDR, 16)
		    || *((u_int16_t *)(htlc->sessionkey + 16)) != htlc->sockaddr.SIN_PORT) {
#else
		if (*((u_int32_t *)(htlc->sessionkey)) != htlc->sockaddr.SIN_ADDR.S_ADDR
		    || *((u_int16_t *)(htlc->sessionkey + 4)) != htlc->sockaddr.SIN_PORT) {
#endif
			char fakeabuf[HOSTLEN+1], realabuf[HOSTLEN+1];
			struct IN_ADDR fakeinaddr;

#ifdef CONFIG_IPV6
			memcpy(&fakeinaddr.S_ADDR, htlc->sessionkey, 16);
			inet_ntop(AFINET, (char *)&fakeinaddr, fakeabuf, sizeof(fakeabuf));
			inet_ntop(AFINET, (char *)&htlc->sockaddr.SIN_ADDR, realabuf, sizeof(realabuf));
#else
			fakeinaddr.S_ADDR = *((u_int32_t *)(htlc->sessionkey));
			inet_ntoa_r(fakeinaddr, fakeabuf, sizeof(fakeabuf));
			inet_ntoa_r(htlc->sockaddr.SIN_ADDR, realabuf, sizeof(realabuf));
#endif
			hx_printf_prefix(htlc, 0, INFOPREFIX, "Server gave wrong address: %s:%u != %s:%u\n",
					 fakeabuf, ntohs(*((u_int16_t *)(htlc->sessionkey + 4))),
					 realabuf, ntohs(htlc->sockaddr.SIN_PORT));
			/* XXX HACK XXX */
			if (htlc->secure == 2) {
				hx_printf_prefix(htlc, 0, INFOPREFIX, "Possible man-in-the-middle attack! Connecting anyway.\n");
			} else {
				hx_printf_prefix(htlc, 0, INFOPREFIX, "Possible man-in-the-middle attack! Closing connection. Use -f to force connect.\n");
				hx_htlc_close(htlc);
				memset(htlc->password, 0, sizeof(htlc->password));
				return;
			}
		}
		if (task_inerror(htlc)) {
			hx_htlc_close(htlc);
			memset(htlc->password, 0, sizeof(htlc->password));
			return;
		}
		task_new(htlc, rcv_task_login, 0, 0, "login");
		icon16 = htons(htlc->icon);
		if (secure_login) {
			llen = hmac_xxx(login, htlc->login, strlen(htlc->login),
					htlc->sessionkey, sklen, htlc->macalg);
			if (!llen) {
				hx_printf_prefix(htlc, 0, INFOPREFIX,
						 "bad HMAC algorithm %s\n", htlc->macalg);
				hx_htlc_close(htlc);
				memset(htlc->password, 0, sizeof(htlc->password));
				return;
			}
		} else {
			llen = strlen(htlc->login);
			hl_encode(login, htlc->login, llen);
			login[llen] = 0;
		}
		pmaclen = hmac_xxx(password_mac, htlc->password, strlen(htlc->password),
				   htlc->sessionkey, sklen, htlc->macalg);
		if (!pmaclen) {	
			hx_printf_prefix(htlc, 0, INFOPREFIX,
					 "bad HMAC algorithm %s\n", htlc->macalg);
			hx_htlc_close(htlc);
			return;
		}
		hc = 4;
#ifdef CONFIG_COMPRESS
		if (!htlc->compressalg[0] || !strcmp(htlc->compressalg, "NONE")) {
			hx_printf_prefix(htlc, 0, INFOPREFIX,
					 "WARNING: this connection is not compressed\n");
			compressalglistlen = 0;
			goto no_compress;
		}
		if (!c_compress_al_len || !s_compress_al_len) {
no_compress_al:		hx_printf_prefix(htlc, 0, INFOPREFIX,
				 "No compress algorithm from server\n");
			hx_htlc_close(htlc);
			return;
		}
		p = list_n(s_compress_al, s_compress_al_len, 0);
		if (!p || !*p)
			goto no_compress_al;
		s_compressalglen = *p >= sizeof(s_compressalg) ? sizeof(s_compressalg)-1 : *p;
		memcpy(s_compressalg, p+1, s_compressalglen);
		s_compressalg[s_compressalglen] = 0;
		p = list_n(c_compress_al, c_compress_al_len, 0);
		if (!p || !*p)
			goto no_compress_al;
		c_compressalglen = *p >= sizeof(c_compressalg) ? sizeof(c_compressalg)-1 : *p;
		memcpy(c_compressalg, p+1, c_compressalglen);
		c_compressalg[c_compressalglen] = 0;
		if (!valid_compress(c_compressalg)) {
			hx_printf_prefix(htlc, 0, INFOPREFIX,
					 "Bad client compress algorithm %s\n", c_compressalg);
			goto ret_badcompress_a;
		} else if (!valid_compress(s_compressalg)) {
			hx_printf_prefix(htlc, 0, INFOPREFIX,
					 "Bad server compress algorithm %s\n", s_compressalg);
ret_badcompress_a:
			compressalglistlen = 0;
			hx_htlc_close(htlc);
			return;
		} else {
			S16HTON(1, compressalglist);
			compressalglistlen = 2;
			compressalglist[compressalglistlen] = s_compressalglen;
			compressalglistlen++;
			memcpy(compressalglist+compressalglistlen, s_compressalg, s_compressalglen);
			compressalglistlen += s_compressalglen;
		}
no_compress:
		hc++;
#endif
#ifdef CONFIG_CIPHER
		if (!htlc->cipheralg[0] || !strcmp(htlc->cipheralg, "NONE")) {
			hx_printf_prefix(htlc, 0, INFOPREFIX,
					 "WARNING: this connection is not encrypted\n");
			cipheralglistlen = 0;
			goto no_cipher;
		}
		if (!c_cipher_al_len || !s_cipher_al_len) {
no_cal:			hx_printf_prefix(htlc, 0, INFOPREFIX,
					 "No cipher algorithm from server\n");
			hx_htlc_close(htlc);
			return;
		}
		p = list_n(s_cipher_al, s_cipher_al_len, 0);
		if (!p || !*p)
			goto no_cal;
		s_cipheralglen = *p >= sizeof(s_cipheralg) ? sizeof(s_cipheralg)-1 : *p;
		memcpy(s_cipheralg, p+1, s_cipheralglen);
		s_cipheralg[s_cipheralglen] = 0;
		p = list_n(c_cipher_al, c_cipher_al_len, 0);
		if (!p || !*p)
			goto no_cal;
		c_cipheralglen = *p >= sizeof(c_cipheralg) ? sizeof(c_cipheralg)-1 : *p;
		memcpy(c_cipheralg, p+1, c_cipheralglen);
		c_cipheralg[c_cipheralglen] = 0;
		if (!valid_cipher(c_cipheralg)) {
			hx_printf_prefix(htlc, 0, INFOPREFIX,
					 "Bad client cipher algorithm %s\n", c_cipheralg);
			goto ret_badca;
		} else if (!valid_cipher(s_cipheralg)) {
			hx_printf_prefix(htlc, 0, INFOPREFIX,
					 "Bad server cipher algorithm %s\n", s_cipheralg);
ret_badca:
			cipheralglistlen = 0;
			hx_htlc_close(htlc);
			return;
		} else {
			S16HTON(1, cipheralglist);
			cipheralglistlen = 2;
			cipheralglist[cipheralglistlen] = s_cipheralglen;
			cipheralglistlen++;
			memcpy(cipheralglist+cipheralglistlen, s_cipheralg, s_cipheralglen);
			cipheralglistlen += s_cipheralglen;
		}

		/* server key first */
		pmaclen = hmac_xxx(htlc->cipher_decode_key, htlc->password, strlen(htlc->password),
				   password_mac, pmaclen, htlc->macalg);
		htlc->cipher_decode_keylen = pmaclen;
		pmaclen = hmac_xxx(htlc->cipher_encode_key, htlc->password, strlen(htlc->password),
				   htlc->cipher_decode_key, pmaclen, htlc->macalg);
		htlc->cipher_encode_keylen = pmaclen;
no_cipher:
		hc++;
#endif
		memset(htlc->password, 0, sizeof(htlc->password));
		hlwrite(htlc, HTLC_HDR_LOGIN, 0, hc,
			HTLC_DATA_LOGIN, llen, login,
			HTLC_DATA_PASSWORD, pmaclen, password_mac,
#ifdef CONFIG_CIPHER
			HTLS_DATA_CIPHER_ALG, cipheralglistlen, cipheralglist,
#endif
#ifdef CONFIG_COMPRESS
			HTLS_DATA_COMPRESS_ALG, compressalglistlen, compressalglist,
#endif
			HTLC_DATA_NAME, strlen(htlc->name), htlc->name,
			HTLC_DATA_ICON, 2, &icon16);
#ifdef CONFIG_COMPRESS
		if (compressalglistlen) {
			hx_printf_prefix(htlc, 0, INFOPREFIX, "compress: server %s client %s\n",
					 c_compressalg, s_compressalg);
			if (c_compress_al_len) {
				htlc->compress_encode_type = COMPRESS_GZIP;
				compress_encode_init(htlc);
			}
			if (s_compress_al_len) {
				htlc->compress_decode_type = COMPRESS_GZIP;
				compress_decode_init(htlc);
			}
		}
#endif
#ifdef CONFIG_CIPHER
		if (cipheralglistlen) {
			hx_printf_prefix(htlc, 0, INFOPREFIX, "cipher: server %s client %s\n",
					 c_cipheralg, s_cipheralg);
			if (!strcmp(s_cipheralg, "RC4"))
				htlc->cipher_decode_type = CIPHER_RC4;
			else if (!strcmp(s_cipheralg, "BLOWFISH"))
				htlc->cipher_decode_type = CIPHER_BLOWFISH;
			else if (!strcmp(s_cipheralg, "IDEA"))
				htlc->cipher_decode_type = CIPHER_IDEA;
			if (!strcmp(c_cipheralg, "RC4"))
				htlc->cipher_encode_type = CIPHER_RC4;
			else if (!strcmp(c_cipheralg, "BLOWFISH"))
				htlc->cipher_encode_type = CIPHER_BLOWFISH;
			else if (!strcmp(c_cipheralg, "IDEA"))
				htlc->cipher_encode_type = CIPHER_IDEA;
			cipher_encode_init(htlc);
			cipher_decode_init(htlc);
		}
#endif
	} else {
#endif /* CONFIG_HOPE */
		inaddr2str(abuf, &htlc->sockaddr);
		hx_printf_prefix(htlc, 0, INFOPREFIX, "%s:%u: login %s\n",
			  abuf, ntohs(htlc->sockaddr.SIN_PORT), task_inerror(htlc) ? "failed?" : "successful");

		if (!task_inerror(htlc)) {
			hx_chat_new(htlc, 0);
			play_sound(snd_login);
			dh_start(htlc)
				switch (dh_type) {
					case HTLS_DATA_UID:
						dh_getint(uid);
						htlc->uid = uid;
						break;
					case HTLS_DATA_SERVERVERSION:
						dh_getint(htlc->serverversion);
						break;
					case HTLS_DATA_BANNERID:
						break;
					case HTLS_DATA_SERVERNAME:
						hx_printf_prefix(htlc, 0, INFOPREFIX, "servername: %.*s\n", dh_len, dh_data);
						break;
				}
			dh_end()
			if (htlc->clientversion >= 150 && htlc->serverversion < 150) {
				icon16 = htons(htlc->icon);
				hlwrite(htlc, HTLC_HDR_USER_CHANGE, 0, 2,
					HTLC_DATA_NAME, strlen(htlc->name), htlc->name,
					HTLC_DATA_ICON, 2, &icon16);
			}
		hx_output.on_connect(htlc);
		}
#ifdef CONFIG_HOPE
	}
#endif
}