int main(int argc, char **argv) { gdk_init(NULL, NULL); /* Force to output original string, usually are Traditional Chinese */ if (strstr(argv[0],"hime-trad")) send_hime_message(GDK_DISPLAY(), TRAD_OUTPUT_TOGGLE); /* Force to output Simplified Chinese */ if (strstr(argv[0],"hime-sim")) send_hime_message(GDK_DISPLAY(), SIM_OUTPUT_TOGGLE); /* Toggle between Original string and Simplified Chinese */ if (strstr(argv[0],"hime-gb-toggle")) send_hime_message(GDK_DISPLAY(), GB_OUTPUT_TOGGLE); /* Toggle virtual keyboard */ if (strstr(argv[0],"hime-kbm-toggle")) send_hime_message(GDK_DISPLAY(), KBM_TOGGLE); if (strstr(argv[0],"hime-exit")) { Display *dpy = GDK_DISPLAY(); if (find_hime_window(dpy)==None) return 0; send_hime_message(dpy, HIME_EXIT_MESSAGE); } return 0; }
static HIME_client_handle *hime_im_client_reopen(HIME_client_handle *hime_ch, Display *dpy) { // dbg("hime_im_client_reopen\n"); int dbg_msg = getenv("HIME_CONNECT_MSG_ON") != NULL; int sockfd=0; int servlen; // char *addr; Server_IP_port srv_ip_port; #if DEBUG u_char *pp; #endif int uid = getuid(); if (uid > 0 && uid < 500) { is_special_user = TRUE; } int tcp = FALSE; HIME_client_handle *handle; int rstatus; // dbg("hime_im_client_reopen\n"); if (!dpy) { dbg("null disp %d\n", hime_ch->fd); goto next; } Atom hime_addr_atom = get_hime_addr_atom(dpy); Window hime_win = None; #define MAX_TRY 3 int loop; if (!is_special_user) for(loop=0; loop < MAX_TRY; loop++) { if ((hime_win=find_hime_window(dpy))!=None || getenv("HIME_IM_CLIENT_NO_AUTO_EXEC")) break; static time_t exec_time; if (time(NULL) - exec_time > 1 /* && count < 5 */) { time(&exec_time); dbg("XGetSelectionOwner: old version of hime or hime is not running ??\n"); static char execbin[]=HIME_BIN_DIR"/hime"; dbg("... try to start a new hime server %s\n", execbin); int pid; if ((pid=fork())==0) { setenv("HIME_DAEMON", "", TRUE); execl(execbin, "hime", NULL); } else { int status; // hime will daemon() waitpid(pid, &status, 0); } } } if (loop == MAX_TRY || hime_win == None) { goto next; } Atom actual_type; int actual_format; u_long nitems,bytes_after; char *message_sock = NULL; Atom hime_sockpath_atom = get_hime_sockpath_atom(dpy); // printf("hime_sockpath_atom %d\n", hime_sockpath_atom); if (!hime_sockpath_atom || XGetWindowProperty(dpy, hime_win, hime_sockpath_atom, 0, 64, False, AnyPropertyType, &actual_type, &actual_format, &nitems,&bytes_after,(u_char **)&message_sock) != Success) { #if DBG || 1 dbg("XGetWindowProperty 2: old version of hime or hime is not running ??\n"); #endif goto next; } Server_sock_path srv_sock_path; srv_sock_path.sock_path[0] = 0; if (message_sock) { memcpy(&srv_sock_path, message_sock, sizeof(srv_sock_path)); XFree(message_sock); } else goto next; struct sockaddr_un serv_addr; bzero((char *) &serv_addr,sizeof(serv_addr)); serv_addr.sun_family = AF_UNIX; char sock_path[UNIX_PATH_MAX]; if (srv_sock_path.sock_path[0]) { strcpy(sock_path, srv_sock_path.sock_path); } else { get_hime_im_srv_sock_path(sock_path, sizeof(sock_path)); } // addr = sock_path; strcpy(serv_addr.sun_path, sock_path); #ifdef SUN_LEN servlen = SUN_LEN(&serv_addr); #else servlen = strlen(serv_addr.sun_path) + sizeof(serv_addr.sun_family); #endif if ((sockfd = socket(AF_UNIX, SOCK_STREAM, 0)) < 0) { perror("cannot open socket"); goto tcp; } if (connect(sockfd, (struct sockaddr *)&serv_addr, servlen) < 0) { close(sockfd); sockfd = 0; goto tcp; } if (dbg_msg) dbg("connected to unix socket addr %s\n", sock_path); goto next; char *message; tcp: message = NULL; if (!hime_addr_atom || XGetWindowProperty(dpy, hime_win, hime_addr_atom, 0, 64, False, AnyPropertyType, &actual_type, &actual_format, &nitems,&bytes_after,(u_char **)&message) != Success) { #if DBG || 1 dbg("XGetWindowProperty: old version of hime or hime is not running ??\n"); #endif goto next; } if (message) { memcpy(&srv_ip_port, message, sizeof(srv_ip_port)); XFree(message); } else goto next; // dbg("im server tcp port %d\n", ntohs(srv_ip_port.port)); struct sockaddr_in in_serv_addr; bzero((char *) &in_serv_addr, sizeof(in_serv_addr)); in_serv_addr.sin_family = AF_INET; in_serv_addr.sin_addr.s_addr = srv_ip_port.ip; in_serv_addr.sin_port = srv_ip_port.port; servlen = sizeof(in_serv_addr); if ((sockfd = socket(AF_INET, SOCK_STREAM, 0)) < 0) { perror("cannot open socket"); goto next; } dbg("sock %d\n", sockfd); if (connect(sockfd, (struct sockaddr *)&in_serv_addr, servlen) < 0) { dbg("hime_im_client_open cannot open: ") ; perror(""); close(sockfd); sockfd = 0; goto next; } #if DEBUG pp = (u_char *)&srv_ip_port.ip; if (dbg_msg) dbg("hime client connected to server %d.%d.%d.%d:%d\n", pp[0], pp[1], pp[2], pp[3], ntohs(srv_ip_port.port)); #endif tcp = TRUE; next: if (!hime_ch) handle = tzmalloc(HIME_client_handle, 1); else { handle = hime_ch; } if (sockfd < 0) sockfd = 0; if (sockfd > 0) { handle->fd = sockfd; if (tcp) { if (!handle->passwd) handle->passwd = malloc(sizeof(HIME_PASSWD)); memcpy(handle->passwd, &srv_ip_port.passwd, sizeof(srv_ip_port.passwd)); } else { if (handle->passwd) { free(handle->passwd); handle->passwd = NULL; } } } if (handle->fd) { if (BITON(handle->flag, FLAG_HIME_client_handle_has_focus)) hime_im_client_focus_in(handle); hime_im_client_set_flags(handle, flags_backup, &rstatus); } return handle; }