Exemple #1
0
struct rpc *rpc_create(const char *host, uint16_t port)
{
    int ret;
    char str_ip[INET_ADDRSTRLEN];
    struct skt_connection *sc;
    struct rpc *r = CALLOC(1, struct rpc);
    if (!r) {
        loge("malloc failed!\n");
        return NULL;
    }
    sc = skt_tcp_connect(host, port);
    if (sc == NULL) {
        loge("connect failed!\n");
        return NULL;
    }
    r->fd = sc->fd;

    if (-1 == skt_set_noblk(sc->fd, 0)) {
        loge("block skt_recv failed!\n");
    }
    ret = rpc_recv(r, r->packet.header.uuid_src, MAX_UUID_LEN);
    if (ret != MAX_UUID_LEN) {
        loge("rpc_recv failed: ret = %d\n", ret);
    }
//    if (-1 == skt_set_noblk(sc->fd, 1)) {
//        loge("no-block skt_recv failed!\n");
//    }
    skt_addr_ntop(str_ip, sc->local.ip);
    logi("local addr = %s:%d, uuid_src = %s\n", str_ip, sc->local.port, r->packet.header.uuid_src);
    skt_addr_ntop(str_ip, sc->remote.ip);
    //logd("remote ip = %s, port = %d\n", str_ip, sc->remote.port);
    r->evbase = gevent_base_create();

    return r;
}
Exemple #2
0
static int on_peer_post_msg_resp(struct rpc *r, void *arg, int len)
{
    pthread_t tid;
    struct p2p *p2p = _p2p;
    uint32_t peer_id;
    char localip[MAX_ADDR_STRING];
    char reflectip[MAX_ADDR_STRING];
    struct sockaddr_in si;
    logi("on_peer_post_msg_resp len = %d\n", len);
    struct nat_info *nat = (struct nat_info *)arg;
    logi("get nat info from peer\n");
    logi("nat.uuid = 0x%08x\n", nat->uuid);
    skt_addr_ntop(localip, nat->local.ip);
    skt_addr_ntop(reflectip, nat->reflect.ip);
    logi("nat.type = %d\n", nat->type);
    logi("nat.local_addr %s:%d\n", localip, nat->local.port);
    logi("nat.reflect_addr %s:%d\n", reflectip, nat->reflect.port);
    p2p->ps = ptcp_socket_by_fd(p2p->nat.fd);
    if (p2p->ps == NULL) {
        loge("error!\n");
        return -1;
    }
    if (p2p->rpc_state == P2P_RPC_SYN_SENT) {//client
        logi("as p2p client\n");
        sleep(1);
        if (_p2p_connect(p2p, localip, nat->local.port)) {
            loge("_p2p_connect nat.local failed, try nat.reflect\n");
            if (_p2p_connect(p2p, reflectip, nat->reflect.port)) {
                logi("_p2p_connect nat.reflect failed too\n");
                return -1;
            }
        }
        return 0;
    }
//server
    logi("as p2p server\n");
    peer_id = nat->uuid;
    p2p_connect(p2p, peer_id);

    si.sin_family = AF_INET;
    si.sin_addr.s_addr = inet_addr(_local_ip);
    si.sin_port = htons(_local_port);

    logi("ptcp_bind %s:%d\n", _local_ip, _local_port);
    ptcp_bind(p2p->ps, (struct sockaddr*)&si, sizeof(si));
    ptcp_listen(p2p->ps, 0);
    pthread_create(&tid, NULL, tmp_thread, p2p);
    return 0;
}
Exemple #3
0
struct rpc *rpc_connect_create(struct rpcd *rpcd, int fd, uint32_t ip, uint16_t port)
{
    char str_ip[INET_ADDRSTRLEN];
    char uuid[MAX_UUID_LEN];
    int ret;

    struct rpc *r = (struct rpc *)calloc(1, sizeof(struct rpc));
    if (!r) {
        loge("malloc failed!\n");
        return NULL;
    }
    r->fd = fd;
    create_uuid(uuid, MAX_UUID_LEN, fd, ip, port);
    struct gevent *e = gevent_create(fd, on_recv, NULL, on_error, (void *)r);
    if (-1 == gevent_add(rpcd->evbase, e)) {
        loge("event_add failed!\n");
    }
    r->ev = e;
    rpc_header_format(r, uuid, uuid, 0, 0);
    ret = rpc_send(r, uuid, MAX_UUID_LEN);
    if (ret != MAX_UUID_LEN) {
        loge("rpc_send failed!\n");
    }
    rpcd_connect_add(rpcd, r, fd, uuid);
    skt_addr_ntop(str_ip, ip);
    logi("on_connect fd = %d, remote_addr = %s:%d, uuid=%s\n", fd, str_ip, port, uuid);

    return r;
}
Exemple #4
0
void on_rpc_read(int fd, void *arg)
{
    pthread_t tid;
    struct p2p *p2p = (struct p2p *)arg;
    struct rpc *r = p2p->rpc;
    char *peer_id;
    char localip[MAX_ADDR_STRING];
    char reflectip[MAX_ADDR_STRING];
    struct sockaddr_in si;
    struct iobuf *buf = rpc_recv_buf(r);
    if (!buf) {
        printf("rpc_recv_buf failed!\n");
        return;
    }
    struct nat_info *nat = (struct nat_info *)buf->addr;
    printf("peer info\n");
    printf("nat.uuid = %s\n", nat->uuid);
    skt_addr_ntop(localip, nat->local.ip);
    skt_addr_ntop(reflectip, nat->reflect.ip);
    printf("nat.type = %d, local.ip = %s, port = %d\n",
            nat->type, localip, nat->local.port);
    printf("reflect.ip = %s, port = %d\n",
            reflectip, nat->reflect.port);
    p2p->ps = ptcp_socket_by_fd(p2p->nat.fd);
    if (p2p->ps == NULL) {
        printf("error!\n");
        return;
    }
    if (p2p->rpc_state == P2P_RPC_SYN_SENT) {//client
        sleep(1);
        _p2p_connect(p2p, reflectip, nat->reflect.port);
        return;
    }
//server
    peer_id = nat->uuid;
    p2p_connect(p2p, peer_id);

    si.sin_family = AF_INET;
    si.sin_addr.s_addr = inet_addr(_local_ip);
    si.sin_port = htons(_local_port);

    printf("ptcp_bind %s:%d\n", _local_ip, _local_port);
    ptcp_bind(p2p->ps, (struct sockaddr*)&si, sizeof(si));
    ptcp_listen(p2p->ps, 0);
    pthread_create(&tid, NULL, tmp_thread, p2p);
}
Exemple #5
0
struct p2p *p2p_init(const char *rpc_srv, const char *stun_srv)
{
    char ip[64];
    struct skt_addr tmpaddr;
    static stun_addr _mapped;
    struct p2p *p2p = CALLOC(1, struct p2p);
    if (!p2p) {
        loge("malloc failed: %d\n", errno);
        return NULL;
    }

    p2p->rpc = rpc_create(rpc_srv, _rpc_port);
    if (!p2p->rpc) {
        loge("rpc_create failed\n");
        return NULL;
    }
    RPC_REGISTER_MSG_MAP(BASIC_RPC_API_RESP);
    rpc_set_cb(p2p->rpc, on_rpc_read, on_rpc_write, on_rpc_error, p2p);
    skt_getaddr_by_fd(p2p->rpc->fd, &tmpaddr);
    skt_addr_ntop(_local_ip, tmpaddr.ip);
    //_local_port = tmpaddr.port;
    //logi("_local_port = %d\n", _local_port);

    stun_init(stun_srv);
    p2p->nat.type = stun_nat_type();
    p2p->nat.uuid = p2p->rpc->send_pkt.header.uuid_src;
    p2p->nat.local.ip = skt_addr_pton(_local_ip);

    _local_port = random_port();
    p2p->nat.local.port = _local_port;
    p2p->nat.fd = stun_socket(_local_ip, _local_port, &_mapped);
    _mapped.addr = ntohl(_mapped.addr);
    skt_addr_ntop(ip, _mapped.addr);
    p2p->nat.reflect.ip = _mapped.addr;
    p2p->nat.reflect.port = _mapped.port;
    logi("get nat info from local\n");
    logi("nat.type = %d\n", p2p->nat.type);
    logi("nat.local_addr %s:%d\n", _local_ip, p2p->nat.local.port);
    logi("nat.reflect_addr %s:%d\n", ip, p2p->nat.reflect.port);
    p2p->rpc_state = P2P_RPC_INIT;
    _p2p = p2p;
    return p2p;
}
Exemple #6
0
struct rpc *rpc_create(const char *host, uint16_t port)
{
    char local_ip[INET_ADDRSTRLEN];
    char remote_ip[INET_ADDRSTRLEN];
    struct rpc *r = CALLOC(1, struct rpc);
    if (!r) {
        loge("malloc failed!\n");
        return NULL;
    }
    memset(&r->recv_pkt, 0, sizeof(struct rpc_packet));
    struct skt_connection *connect;
    connect = skt_tcp_connect(host, port);
    if (!connect) {
        loge("connect failed!\n");
        return NULL;
    }
    r->fd = connect->fd;
    if (-1 == skt_set_block(r->fd)) {
        loge("skt_set_block failed!\n");
    }

    r->evbase = gevent_base_create();
    if (!r->evbase) {
        loge("gevent_base_create failed!\n");
        return NULL;
    }
    rpc_set_cb(r, on_read, on_write, on_error, r);
    r->dispatch_thread = thread_create("rpc_dispatch", rpc_dispatch_thread, r);

    r->state = rpc_inited;
    if (thread_sem_wait(r->dispatch_thread, 2000) == -1) {
        loge("wait response failed %d:%s\n", errno, strerror(errno));
        return NULL;
    }
    skt_addr_ntop(local_ip, connect->local.ip);
    skt_addr_ntop(remote_ip, connect->remote.ip);
    logi("rpc[%08x] connect information:\n", r->send_pkt.header.uuid_src);
    logi("local addr = %s:%d\n", local_ip, connect->local.port);
    logi("remote addr = %s:%d\n", remote_ip, connect->remote.port);

    return r;
}
Exemple #7
0
static int udp_open(struct protocol_ctx *sc, const char *url)
{
    struct udp_ctx *c = sc->priv;
    struct skt_addr addr;
    skt_addr_list_t *tmp;
    char str[MAX_ADDR_STRING];
    int len;
    char *p;
    char *tag = ":";
    p = strstr(url, tag);
    if (!p) {
        printf("udp url is invalid\n");
        return -1;
    }
    len = p - url;//"127.0.0.1:2333"
    printf("url = %s, len = %d\n", url, len);
    strncpy(c->dst_ip, url, len);
    p += strlen(tag);
    c->dst_port = atoi(p);

    if (0 == skt_get_local_list(&tmp, 0)) {
        for (; tmp; tmp = tmp->next) {
            skt_addr_ntop(str, tmp->addr.ip);
            printf("ip = %s port = %d\n", str, tmp->addr.port);
        }
    }
    strcpy(c->src_ip, str);
    c->fd = skt_udp_bind(str, c->dst_port, 0);
    if (c->fd == -1) {
        printf("bind %s failed\n", str);
        return -1;
    }
    printf("bind fd = %d\n", c->fd);
    sc->fd = c->fd;
    skt_get_addr_by_fd(&addr, c->fd);
    c->src_port = addr.port;
//    skt_set_noblk(c->fd, 1);
//    skt_set_reuse(c->fd, 1);
    printf("url: \"udp://%s:%d?localport=%d\"\n", c->src_ip, c->src_port, c->dst_port);
    return 0;
}