コード例 #1
0
ファイル: attr.c プロジェクト: ClearwaterCore/libre-upstream
int stun_attr_encode(struct mbuf *mb, uint16_t type, const void *v,
		     const uint8_t *tid, uint8_t padding)
{
	const struct stun_change_req *ch_req = v;
	const struct stun_errcode *err_code = v;
	const struct stun_unknown_attr *ua = v;
	const unsigned int *num = v;
	const struct mbuf *mbd = v;
	size_t start, len;
	uint32_t i, n;
	int err = 0;

	if (!mb || !v)
		return EINVAL;

	mb->pos += 4;
	start = mb->pos;

	switch (type) {

	case STUN_ATTR_MAPPED_ADDR:
	case STUN_ATTR_ALT_SERVER:
	case STUN_ATTR_RESP_ORIGIN:
	case STUN_ATTR_OTHER_ADDR:
		tid = NULL;
		/*@fallthrough@*/
	case STUN_ATTR_XOR_PEER_ADDR:
	case STUN_ATTR_XOR_RELAY_ADDR:
	case STUN_ATTR_XOR_MAPPED_ADDR:
		err |= stun_addr_encode(mb, v, tid);
		break;

	case STUN_ATTR_CHANGE_REQ:
		n = (uint32_t)ch_req->ip << 2 | (uint32_t)ch_req->port << 1;
		err |= mbuf_write_u32(mb, htonl(n));
		break;

	case STUN_ATTR_USERNAME:
	case STUN_ATTR_REALM:
	case STUN_ATTR_NONCE:
	case STUN_ATTR_SOFTWARE:
		err |= mbuf_write_str(mb, v);
		break;

	case STUN_ATTR_MSG_INTEGRITY:
		err |= mbuf_write_mem(mb, v, 20);
		break;

	case STUN_ATTR_ERR_CODE:
		err |= mbuf_write_u16(mb, 0x00);
		err |= mbuf_write_u8(mb,  err_code->code/100);
		err |= mbuf_write_u8(mb,  err_code->code%100);
		err |= mbuf_write_str(mb, err_code->reason);
		break;

	case STUN_ATTR_UNKNOWN_ATTR:
		for (i=0; i<ua->typec; i++)
			err |= mbuf_write_u16(mb, htons(ua->typev[i]));
		break;

	case STUN_ATTR_CHANNEL_NUMBER:
	case STUN_ATTR_RESP_PORT:
		err |= mbuf_write_u16(mb, htons(*num));
		err |= mbuf_write_u16(mb, 0x0000);
		break;

	case STUN_ATTR_LIFETIME:
	case STUN_ATTR_PRIORITY:
	case STUN_ATTR_FINGERPRINT:
		err |= mbuf_write_u32(mb, htonl(*num));
		break;

	case STUN_ATTR_DATA:
	case STUN_ATTR_PADDING:
		if (mb == mbd) {
			mb->pos = mb->end;
			break;
		}
		err |= mbuf_write_mem(mb, mbuf_buf(mbd), mbuf_get_left(mbd));
		break;

	case STUN_ATTR_REQ_ADDR_FAMILY:
	case STUN_ATTR_REQ_TRANSPORT:
		err |= mbuf_write_u8(mb, *num);
		err |= mbuf_write_u8(mb, 0x00);
		err |= mbuf_write_u16(mb, 0x0000);
		break;

	case STUN_ATTR_EVEN_PORT:
		err |= mbuf_write_u8(mb, ((struct stun_even_port *)v)->r << 7);
		break;

	case STUN_ATTR_DONT_FRAGMENT:
	case STUN_ATTR_USE_CAND:
		 /* no value */
		break;

	case STUN_ATTR_RSV_TOKEN:
	case STUN_ATTR_CONTROLLED:
	case STUN_ATTR_CONTROLLING:
		err |= mbuf_write_u64(mb, sys_htonll(*(uint64_t *)v));
		break;

	default:
		err = EINVAL;
		break;
	}

	/* header */
	len = mb->pos - start;

	mb->pos = start - 4;
	err |= mbuf_write_u16(mb, htons(type));
	err |= mbuf_write_u16(mb, htons(len));
	mb->pos += len;

	/* padding */
	while ((mb->pos - start) & 0x03)
		err |= mbuf_write_u8(mb, padding);

	return err;
}
コード例 #2
0
ファイル: sys.c プロジェクト: traviscross/libre-test
int test_sys_endian(void)
{
	uint16_t s_le, s_ho;
	uint8_t *s = (uint8_t *)&s_le;
	uint32_t l_le, l_ho;
	uint8_t *l = (uint8_t *)&l_le;
	uint64_t ll0, ll1 = 0x0102030405060708ULL;

	/* Little endian: LSB first - 0x1234
	 *
	 * 0x0000: 0x34
	 * 0x0001: 0x12
	 */

	s[0] = 0x34;
	s[1] = 0x12;

	s_ho = sys_ltohs(s_le);
	if (0x1234 != s_ho) {
		DEBUG_WARNING("endian short: 0x%04x\n", s_ho);
		return EINVAL;
	}

	if (s_le != sys_htols(s_ho)) {
		DEBUG_WARNING("sys_htols failed: 0x%04x\n", sys_htols(s_ho));
		return EINVAL;
	}

	/* 0x12345678
	 *
	 * 0x0000: 0x78
	 * 0x0001: 0x56
	 * 0x0002: 0x34
	 * 0x0003: 0x12
	 */

	l[0] = 0x78;
	l[1] = 0x56;
	l[2] = 0x34;
	l[3] = 0x12;

	l_ho = sys_ltohl(l_le);
	if (0x12345678 != l_ho) {
		DEBUG_WARNING("endian long: 0x%08x\n", l_ho);
		return EINVAL;
	}

	if (l_le != sys_htoll(l_ho)) {
		DEBUG_WARNING("sys_htoll failed: 0x%08x\n", sys_htoll(l_ho));
		return EINVAL;
	}

	/* Test 64-bit */
	ll0 = sys_ntohll(sys_htonll(ll1));

	if (ll0 != ll1) {
		DEBUG_WARNING("endian long-long: 0x%llx\n", ll0);
		return EINVAL;
	}

	return 0;
}