예제 #1
0
파일: chat.c 프로젝트: wyat/kbs
void call_query_ByChatid(chatcontext * pthis, const char *arg)
{                               /* add by dong, 1998.9.12 */
    char uident[32];
    char tmpstr[40];
    int res;

    if (!*arg) {
        printchatline(pthis, "*** 请输入要查询的chat ID ***");
        return;
    }
    strncpy(uident, arg, 32);
    uident[31] = '\0';
    /* get user id from the chat id */
    sprintf(tmpstr, "/qc %s", uident);
    chat_send(pthis, tmpstr);
    res = chat_recv(pthis, tmpstr, 40);
    if (res <= 0)
        return;
    tmpstr[res] = '\0';
    if (tmpstr[0] == '1') {
        sprintf(uident, "%s", tmpstr + 1);
    } else {
        sprintf(genbuf, "\033[32m这个chat ID不存在!\033[m");
        printchatline(pthis, genbuf);
        return;
    }
    query_user(pthis, uident);
}
예제 #2
0
파일: chat.c 프로젝트: wyat/kbs
int chat_status(struct user_info *uentp, chatcontext * pthis)
{
    char tmpstr[31],buf[80],buf2[80];
    char *lpTmp;

    if (strlen(genbuf)>t_columns)
        return QUIT;
    if (uentp->invisible == 1) {
        if (HAS_PERM(getCurrentUser(), PERM_SEECLOAK)) {
            sprintf(genbuf + strlen(genbuf), "\x1b[32m#\x1b[m");
        } else
            return 0;
    }
    lpTmp = (char *) idle_str(buf,uentp);
    if (uentp->in_chat) {       /* add by Luzi 1997.11.18 */
        int res;

        sprintf(tmpstr, "/q %s", uentp->userid);
        chat_send(pthis, tmpstr);
        res = chat_recv(pthis, tmpstr, 30);
        if (res <= 0)
            return -1;
        tmpstr[res] = '\0';
        if (tmpstr[0] == '1') {
            sprintf(genbuf + strlen(genbuf), "'%s' room as '%s'",
                    tmpstr + 1, uentp->chatid);
            if (lpTmp[0] != ' ')
                sprintf(genbuf + strlen(genbuf), "[%s];", lpTmp);
            else
                strcat(genbuf, " ;");
            return COUNT;
        }
    }
    sprintf(genbuf, "%s%-8s", genbuf, modestring(buf2,uentp->mode, uentp->destuid, 0,        /* 1->0 不显示聊天对象等 modified by dong 1996.10.26 */
            (uentp->in_chat ? uentp->
             chatid : NULL)));
    if (lpTmp[0] != ' ')
        sprintf(genbuf + strlen(genbuf), "[%s];", lpTmp);
    else
        strcat(genbuf, " ;");
    return COUNT;
}
예제 #3
0
파일: chat.c 프로젝트: wyat/kbs
/* 2001/5/6 --wwj, 修改 ent_chat 函数 */
int ent_chat_conn(chatcontext * pthis, int chatnum)
{
    struct sockaddr_in sin;
    int ch;
    char inbuf[128], *ptr;

    memset(&sin, 0, sizeof sin);
    sin.sin_family = PF_INET;
    sin.sin_addr.s_addr = htonl(INADDR_LOOPBACK);
    /*
        sin.sin_addr.s_addr = inet_addr("166.111.8.237");
    */
    if (chatnum == 1)
        sin.sin_port = htons(CHATPORT3);
    else
        sin.sin_port = htons(CHATPORT2);
    pthis->cfd = socket(sin.sin_family, SOCK_STREAM, 0);
    if (connect(pthis->cfd, (struct sockaddr *) &sin, sizeof sin)) {    /*如果连接 chatd 失败,则启动chatd */
        close(pthis->cfd);
        switch (ch = fork()) {
            case -1 /*fork failure */ :
                bbslog("chatd", "fork error");
                break;
            case 0 /*fork success */ :
                bbslog("chatd", "fork success");
                prints("开启聊天室...");
                if (chatnum == 1)
                    system("bin/chatd");
                else
                    system("bin/chatd 2");
                exit(1);
            default:
                bbslog("chatd", "fork par-proc");
                /* The chat daemon forks so we can wait on it here. */
                waitpid(ch, NULL, 0);
        }
        pthis->cfd = socket(sin.sin_family, SOCK_STREAM, 0);
        if ((connect(pthis->cfd, (struct sockaddr *) &sin, sizeof sin))) {
            close(pthis->cfd);
            bbslog("chatd", "connect2 failed %d", errno);
            return -1;
        }
    }
    /* Leeward 98.04.26 */
    move(3, 0);
    clrtoeol();
    move(4, 0);                 /* Leave line 3 for error message while entering chat room */
    prints
    ("输入字符 \033[1m\033[37m*\033[m 再按 \033[1m\033[37mEnter\033[m 可以取消进入聊天室。                                    ");
    clrtoeol();
    move(5, 0);
    clrtoeol();                 /* Clear line 5 for good looking */
    while (1) {
        int gdataret;
        gdataret = getdata(2, 0, "请输入聊天代号:", inbuf, 9, DOECHO, NULL, true);
        if (gdataret == -1 || '*' == inbuf[0]) {  /* Leeward 98.04.26 */
            close(pthis->cfd);
            return 0;
        }
        if (inbuf[0] != '\0' && inbuf[0] != '\n' && inbuf[0] != '/') {
            strncpy(pthis->chatid, inbuf, 8);
        } else {
            strncpy(pthis->chatid, getCurrentUser()->userid, 8);
        }
        pthis->chatid[8] = '\0';
        sprintf(inbuf, "/! %d %d %s %s", uinfo.uid, getCurrentUser()->userlevel,
                getCurrentUser()->userid, pthis->chatid);
        chat_send(pthis, inbuf);        /* send user info to chatd , and chatd will check it */
        if (chat_recv(pthis, inbuf, 3) != 3) {
            close(pthis->cfd);
            return 0;
        }
        if (!strcmp(inbuf, CHAT_LOGIN_OK))
            break;
        else if (!strcmp(inbuf, CHAT_LOGIN_EXISTS))
            ptr = "这个代号已经有人用了";
        else if (!strcmp(inbuf, CHAT_LOGIN_INVALID))
            ptr = "这个代号是错误的";
        else
            ptr =
                "已经有一个窗口在聊天室里了(若非如此请退出BBS重新登录;若还不行再找在线站长)";
        move(3, 0);
        prints(ptr);
        clrtoeol();
        bell();
    }
    return 1;
}
예제 #4
0
파일: chat.c 프로젝트: wyat/kbs
int chat_parse(chatcontext * pthis)
{
    int len;
    char *bptr;

    if (!pthis->bufptr || pthis->buf[pthis->bufptr - 1] != 0) {
        if (chat_recv(pthis, NULL, 0) < 0)
            return -1;
    }
    len = 0;
    bptr = pthis->buf;
    while (bptr < pthis->buf + pthis->bufptr) {
        for (len = 0; bptr + len < pthis->buf + pthis->bufptr; len++) {
            if (!bptr[len]) {
                len = -len;
                break;
            }
        }
        if (len > 0)
            break;
        len = -len + 1;         /* skip 0 */
        if (*bptr == '/') {     /* 处理server传来的命令 */
            switch (bptr[1]) {
                case 'p':
                    /* add by KCN for list long emote */
                    /* chat_waitkey(pthis);  removed by wwj */
                    break;
                case 'c':
                    chat_clear(pthis);
                    break;
                case 'n':
                    strncpy(pthis->chatid, bptr + 2, 8);
                    pthis->chatid[8] = 0;
                    print_chatid(pthis);
                    clrtoeol();
                    uinfo.in_chat = true;
                    strcpy(uinfo.chatid, pthis->chatid);
                    UPDATE_UTMP_STR(chatid, uinfo);
                    break;
                case 'r':
                    strncpy(pthis->chatroom, bptr + 2, IDLEN - 1);
                    break;
                case 'z':
                    strncpy(pthis->chatroom, bptr + 2, IDLEN - 1);
                    /* fall throw */
                case 't':
                    move(0, 0);
                    clrtoeol();
                    if (bptr[1] == 't')
                        strcpy(pthis->topic, bptr + 2);
                    prints
                    ("\033[44m\033[33m 房间: \033[36m%-10s  \033[33m话题:\033[36m%-51s\033[31m%2s\033[m",
                     pthis->chatroom, pthis->topic,
                     (pthis->rec) ? "录" : "  ");
                    break;
            }
        } else {
            printchatline(pthis, bptr);
        }
        bptr += len;
        len = 0;
    }
    if (len > 0) {
        memcpy(pthis->buf, bptr, pthis->bufptr - (bptr - pthis->buf));
        pthis->bufptr -= bptr - pthis->buf;
    } else {
        pthis->bufptr = 0;
    }
    return 0;
}
void server(int port)
{
    linked_list_t *mapcycle_list = NULL;
    parse_mapcycle(&mapcycle_list);
    node_t *current_map = mapcycle_list->head;
    char port_game[100];
    char port_chat[100];
    char port_map[100];
    sprintf(port_game, "%d", port);
    sprintf(port_chat, "%d", port + 1);
    sprintf(port_map,  "%d", port + 2);
    signal(SIGTERM, sighandler);
    signal(SIGINT, sighandler);
    //node_t *current_map = mapcycle_list->head->next;
    while(server_running){
        printf("[SERVER] NEW GAME\n");
        player_list = malloc(sizeof(linked_list_t));
        observer_list = malloc(sizeof(linked_list_t));
        list_init(player_list);
        list_init(observer_list);
        int game_server_socket = prepare_server_UDP(port_game, AF_INET6);
        int chat_server_socket = prepare_server_TCP(port_chat, AF_INET6);
        int map_server_socket  = prepare_server_TCP(port_map , AF_INET6);

        current_map = current_map->next;
        if(current_map == mapcycle_list->tail){
            current_map = mapcycle_list->head->next;
        }
        game_server_init(current_map->data);

        fd_set descriptors_set;
        FD_ZERO(&descriptors_set);
        FD_SET(map_server_socket,  &descriptors_set);
        FD_SET(chat_server_socket, &descriptors_set);
        FD_SET(game_server_socket, &descriptors_set);


        int max_fd = map_server_socket > chat_server_socket ? map_server_socket : chat_server_socket;
        max_fd = max_fd > game_server_socket ? max_fd : game_server_socket;
        struct timeval timeout;
        memset(&timeout, 0, sizeof(struct timeval));
        timeout.tv_sec = 3;
        change_map = 0;
        while(!change_map){
            if(select(max_fd  + 1, &descriptors_set, NULL, NULL, &timeout) < 0) {
                continue;
            }

            timeout.tv_sec = 3;

            if (FD_ISSET(map_server_socket , &descriptors_set)){
                map_server(map_server_socket, current_map_id);
            }

            if (FD_ISSET(chat_server_socket , &descriptors_set)){
                chat_server(chat_server_socket);
            }

            if (FD_ISSET(game_server_socket , &descriptors_set)){
                game_server(game_server_socket);
            }

            for (node_t *i = player_list->head->next; i != player_list->tail; i = i->next){
                player_info_t *player_info = (player_info_t*)i->data;
                if (FD_ISSET(player_info->chat_descriptor , &descriptors_set)){
                    char buffer[129];
                    memset(buffer, 0, 129);
                    int full_recv = 0;
                    int bytes_recv = chat_recv(player_info->chat_descriptor, buffer, &full_recv);
                    if(bytes_recv == 0){
                        //HANDLE DISCONNECT
                        int player_id = player_info->playerID;

                        close(player_info->chat_descriptor);
                        node_t *previous = i->previous;
                        list_remove_node(i, player_list);
                        i = previous;

                        if (player_id == 255){
                            continue;
                        }

                        char buffer[129];
                        sprintf(buffer, "Player %"SCNu8" disconnected", player_id);
                        printf("[CHAT SERVER] %s\n", buffer);
                        broadcast_disconnection_ack(game_server_socket, player_id, player_list);
                        chat_forward_msg(0, buffer, player_list);
                    }else if (bytes_recv < 0){
                        printf("[CHAT SERVER] Error receiving from %"SCNu8"%s\n", player_info->playerID, strerror(errno));
                    }else if (full_recv){
                        if (buffer[2] == '*'){
                            change_map = 1;
                        }
                        if (player_info->playerID == 255){
                            continue;
                        }
                        chat_forward_msg(player_info->playerID, &buffer[2], player_list);
                        gettimeofday(&player_info->last_action, NULL);
                    }
                }
            }

            remove_idle_players(game_server_socket);
            respawn_death_players(game_server_socket);

            FD_ZERO(&descriptors_set);
            FD_SET(map_server_socket,  &descriptors_set);
            FD_SET(chat_server_socket, &descriptors_set);
            FD_SET(game_server_socket, &descriptors_set);
            max_fd = map_server_socket > chat_server_socket ? map_server_socket : chat_server_socket;
            max_fd = max_fd > game_server_socket ? max_fd : game_server_socket;
            for (node_t *i = player_list->head->next; i != player_list->tail; i = i->next){
                player_info_t *player_info = (player_info_t*)i->data;
                FD_SET(player_info->chat_descriptor, &descriptors_set);
                if (player_info->chat_descriptor > max_fd){
                    max_fd = player_info->chat_descriptor;
                }
            }
            if (change_map){
                sleep(5);
                broadcast_map_change(game_server_socket, player_list);
            }
        }
        change_map = 0;
        for(node_t *i = player_list->head->next; i != player_list->tail; i = i->next){
            player_info_t *player_info = (player_info_t*)i->data;
            close(player_info->chat_descriptor);
        }

        list_delete(player_list);
        free(player_list);
        list_delete(observer_list);
        game_server_shutdown();
        free(observer_list);
        close(map_server_socket);
        close(chat_server_socket);
        close(game_server_socket);
    }
    delete_mapcycle_list(&mapcycle_list);
}