/*@ MPI_T_category_get_num - Get the number of categories Output Parameters: . num_cat - current number of categories (integer) .N ThreadSafe .N Errors .N MPI_SUCCESS .N MPI_T_ERR_NOT_INITIALIZED @*/ int MPI_T_category_get_num(int *num_cat) { int mpi_errno = MPI_SUCCESS; MPID_MPI_STATE_DECL(MPID_STATE_MPI_T_CATEGORY_GET_NUM); MPIR_ERRTEST_MPIT_INITIALIZED(mpi_errno); MPIR_T_THREAD_CS_ENTER(); MPID_MPI_FUNC_ENTER(MPID_STATE_MPI_T_CATEGORY_GET_NUM); /* Validate parameters */ # ifdef HAVE_ERROR_CHECKING { MPID_BEGIN_ERROR_CHECKS { MPIR_ERRTEST_ARGNULL(num_cat, "num_cat", mpi_errno); } MPID_END_ERROR_CHECKS } # endif /* HAVE_ERROR_CHECKING */ /* ... body of routine ... */ *num_cat = utarray_len(cat_table); /* ... end of body of routine ... */ fn_exit: MPID_MPI_FUNC_EXIT(MPID_STATE_MPI_T_CATEGORY_GET_NUM); MPIR_T_THREAD_CS_EXIT(); return mpi_errno; fn_fail: /* --BEGIN ERROR HANDLING-- */ # ifdef HAVE_ERROR_CHECKING { mpi_errno = MPIR_Err_create_code( mpi_errno, MPIR_ERR_RECOVERABLE, FCNAME, __LINE__, MPI_ERR_OTHER, "**mpi_t_category_get_num", "**mpi_t_category_get_num %p", num_cat); } # endif mpi_errno = MPIR_Err_return_comm(NULL, FCNAME, mpi_errno); goto fn_exit; /* --END ERROR HANDLING-- */ }
int MPIR_T_category_get_cvars_impl(int cat_index, int len, int indices[]) { int mpi_errno = MPI_SUCCESS; cat_table_entry_t *cat; int i, num_cvars, count; cat = (cat_table_entry_t *)utarray_eltptr(cat_table, cat_index); num_cvars = utarray_len(cat->cvar_indices); count = len < num_cvars ? len : num_cvars; for (i = 0; i < count; i++) { indices[i] = *(int *)utarray_eltptr(cat->cvar_indices, i); } fn_exit: return mpi_errno; fn_fail: goto fn_exit; }
FCITX_EXPORT_API FcitxComposeTable* fcitx_compose_table_new_from_file(const char* systemComposeDir, const char* composeFile, const char* locale) { FcitxComposeTable* table = _fcitx_compose_table_alloc(locale); int nPossibleLocation = 1; const char* possibleLocation[1] = {systemComposeDir}; _fcitx_compose_table_find_system_compose_dir(table, nPossibleLocation, possibleLocation); bool found = _fcitx_compose_table_process_file(table, composeFile); if (found && utarray_len(table->composeTable) == 0) { table->state = FCTS_EmptyTable; } if (!found) { table->state = FCTS_MissingComposeFile; } _fcitx_compose_table_order_compose_table(table); return table; }
/* given an initial hexagon at (xv[pos],yv[pos]), is the neighbor at the given edge occupied? */ int available(int /* item index */ pos, int /* neighbor at */edge, UT_array /* of int */*xv, UT_array /* of int */*yv, int /* output coord*/*ox, int /* output coord*/*oy) { int x = *(int*)utarray_eltptr(xv,pos); // own position: x int y = *(int*)utarray_eltptr(yv,pos); // own position: y get_hextile_neighbor(x,y,edge,ox,oy); // neighbor[edge]=[ox,oy] // scan through xv/yv to see if ox/oy used. TODO hash lookup. int p; for(p=0; p < utarray_len(xv); p++) { x = *(int*)utarray_eltptr(xv,p); y = *(int*)utarray_eltptr(yv,p); if ((x == *ox) && (y == *oy)) return 0; } fprintf(stderr,"attaching to pos:%d/%d\n",pos,edge); return 1; }
FCITX_EXPORT_API int FcitxInstanceAllocDataForIC(FcitxInstance* instance, FcitxICDataAllocCallback allocCallback, FcitxICDataCopyCallback copyCallback, FcitxICDataFreeCallback freeCallback, void* arg) { FcitxICDataInfo info; info.allocCallback = allocCallback; info.copyCallback = copyCallback; info.freeCallback = freeCallback; info.arg = arg; utarray_push_back(&instance->icdata, &info); FcitxInputContext *rec = instance->ic_list; while (rec) { FillICData(instance, rec); rec = rec->next; } return utarray_len(&instance->icdata) - 1; }
Token* container_elem(Token *ary, List *args, int fst, int lst) { log_msg("CMDLINE", "access_container"); Token *get = ary; for (int i = fst; i < lst; i++) { List *accessor = list_arg(args, i, VAR_LIST); if (!accessor || utarray_len(accessor->items) > 1) return NULL; int index = -1; if (!str_num(list_arg(accessor, 0, VAR_STRING), &index)) return NULL; List *ret = token_val(get, VAR_LIST); if (!ret) return NULL; get = tok_arg(ret, index); } return get; }
UT_array* CharSelectDataFind(CharSelectData* charselect, const char* needle) { UnicodeSet *result = NULL; UT_array* returnRes; utarray_new(returnRes, fcitx_int32_icd); char* simplified = Simplified(needle); UT_array* searchStrings = SplitString(simplified); if (strlen(simplified) == 1) { // search for hex representation of the character utarray_clear(searchStrings); char* format = FormatCode(simplified[0], 4, "U+"); utarray_push_back(searchStrings, &format); free(format); } free(simplified); if (utarray_len(searchStrings) == 0) { return returnRes; } utarray_foreach(s, searchStrings, char*) { char* end = NULL; if(IsHexString(*s)) { end = NULL; uint32_t uni = (uint32_t) strtoul(*s + 2, &end, 16); utarray_push_back(returnRes, &uni); // search for "1234" instead of "0x1234" char* news = strdup(*s + 2); free(*s); *s = news; } // try to parse string as decimal number end = NULL; uint32_t unicode = (uint32_t) strtoul(*s, &end, 10); if (*end == '\0') { utarray_push_back(returnRes, &unicode); } }
END_TEST START_TEST (test_fwd) { const zcr_forward_t test_data[] = { {PROTO_TCP, htons(53), 0x04030201, 0, 1}, {PROTO_UDP, htons(53), 0x08070605, 0, 1}, {PROTO_TCP, htons(80), 0x0C0B0A09, htons(83), 1}, {PROTO_UDP, htons(80), 0x100F0E0D, htons(83), 1}, {PROTO_TCP, htons(53), 0, 0, 0}, {PROTO_UDP, htons(53), 0, 0, 0}, {PROTO_TCP, htons(80), 0, 0, 0}, {PROTO_UDP, htons(80), 0, 0, 0}, }; zclient_rule_parser_t *parser = zclient_rule_parser_new(); zclient_rules_t rules; zclient_rules_init(&rules); fail_if(!zclient_rule_parse(parser, &rules, "fwd.tcp.53.1.2.3.4")); fail_if(!zclient_rule_parse(parser, &rules, "fwd.udp.53.5.6.7.8")); fail_if(!zclient_rule_parse(parser, &rules, "fwd.tcp.80.9.10.11.12:83")); fail_if(!zclient_rule_parse(parser, &rules, "fwd.udp.80.13.14.15.16:83")); fail_if(!zclient_rule_parse(parser, &rules, "rmfwd.tcp.53")); fail_if(!zclient_rule_parse(parser, &rules, "rmfwd.udp.53")); fail_if(!zclient_rule_parse(parser, &rules, "rmfwd.tcp.80")); fail_if(!zclient_rule_parse(parser, &rules, "rmfwd.udp.80")); fail_if(!rules.have.fwd_rules, "fwd have fail"); fail_if(ARRAYSIZE(test_data) != utarray_len(&rules.fwd_rules)); for (size_t i = 0; i < ARRAYSIZE(test_data); i++) { zcr_forward_t *rule = *(zcr_forward_t **) utarray_eltptr(&rules.fwd_rules, i); fail_if(test_data[i].add != rule->add, "fwd idx=%u add flag fail", i); fail_if(test_data[i].proto != rule->proto, "fwd idx=%u proto fail", i); fail_if(test_data[i].port != rule->port, "fwd idx=%u port fail", i); fail_if(test_data[i].fwd_ip != rule->fwd_ip, "fwd idx=%u fwd_ip fail (0x%X)", i, rule->fwd_ip); fail_if(test_data[i].fwd_port != rule->fwd_port, "fwd idx=%u fwd_port fail", i); } zclient_rules_destroy(&rules); }
void call_hooks(EventHandler *evh, Plugin *host, Plugin *caller, HookArg *hka) { if (!evh) return; int count = utarray_len(evh->hooks); for (int i = 0; i < count; i++) { Hook *it = (Hook*)utarray_eltptr(evh->hooks, i); if (it->type == HK_CMD) { int id = id_from_plugin(host); if (it->bufno == -1 || (host && id == it->bufno)) call_cmd_hook(it, hka); continue; } if (it->host != host && it->type != HK_TMP) continue; call_intl_hook(it, host, caller, hka); } }
static Value *findOrCreateEntry(ATP_Array *p_array, unsigned int p_index) { Value *l_entry; unsigned int l_length = utarray_len(CAST(p_array)); if (p_index > l_length) { ERR("Index out of bounds\n"); return NULL; } else if (p_index == l_length) { utarray_extend_back(CAST(p_array)); l_entry = (Value *) utarray_back(CAST(p_array)); } else { l_entry = (Value *) utarray_eltptr(CAST(p_array), p_index); } return l_entry; }
END_TEST START_TEST (test_fwd) { const struct zrule_fwd test_data[] = { {PROTO_TCP, htons(53), 0x04030201, 0, 1}, {PROTO_UDP, htons(53), 0x08070605, 0, 1}, {PROTO_TCP, htons(80), 0x0C0B0A09, htons(83), 1}, {PROTO_UDP, htons(80), 0x100F0E0D, htons(83), 1}, {PROTO_TCP, htons(53), 0, 0, 0}, {PROTO_UDP, htons(53), 0, 0, 0}, {PROTO_TCP, htons(80), 0, 0, 0}, {PROTO_UDP, htons(80), 0, 0, 0}, }; struct zcrules rules; crules_init(&rules); fail_if(0 != crules_parse(&rules, "fwd.tcp.53.1.2.3.4"), "fwd parse fail"); fail_if(0 != crules_parse(&rules, "fwd.udp.53.5.6.7.8"), "fwd parse fail"); fail_if(0 != crules_parse(&rules, "fwd.tcp.80.9.10.11.12:83"), "fwd parse fail"); fail_if(0 != crules_parse(&rules, "fwd.udp.80.13.14.15.16:83"), "fwd parse fail"); fail_if(0 != crules_parse(&rules, "rmfwd.tcp.53"), "fwd parse fail"); fail_if(0 != crules_parse(&rules, "rmfwd.udp.53"), "fwd parse fail"); fail_if(0 != crules_parse(&rules, "rmfwd.tcp.80"), "fwd parse fail"); fail_if(0 != crules_parse(&rules, "rmfwd.udp.80"), "fwd parse fail"); fail_if(!rules.have.fwd_rules, "fwd have fail"); fail_if(sizeof(test_data) / sizeof(test_data[0]) != utarray_len(&rules.fwd_rules), "fwd count fail"); for (size_t i = 0; i < sizeof(test_data) / sizeof(test_data[0]); i++) { struct zrule_fwd *rule = *(struct zrule_fwd **) utarray_eltptr(&rules.fwd_rules, i); fail_if(test_data[i].add != rule->add, "fwd idx=%u add flag fail", i); fail_if(test_data[i].proto != rule->proto, "fwd idx=%u proto fail", i); fail_if(test_data[i].port != rule->port, "fwd idx=%u port fail", i); fail_if(test_data[i].fwd_ip != rule->fwd_ip, "fwd idx=%u fwd_ip fail (0x%X)", i, rule->fwd_ip); fail_if(test_data[i].fwd_port != rule->fwd_port, "fwd idx=%u fwd_port fail", i); } crules_free(&rules); }
static Cmdret conf_color(List *args, Cmdarg *ca) { log_msg("CONFIG", "conf_color"); if (utarray_len(args->items) < 3) return NORET; int fg, bg; int ret = 0; ret += str_num(list_arg(args, 2, VAR_STRING), &fg); ret += str_num(list_arg(args, 3, VAR_STRING), &bg); char *group = list_arg(args, 1, VAR_STRING); if (!ret || !group) return NORET; fn_group *grp = get_group(group); if (!grp) return NORET; //TODO: error msg set_color(grp, fg, bg); //TODO: refresh cached colors return NORET; }
boolean MainMenuAction(FcitxUIMenu* menu, int index) { FcitxLightUI* lightui = (FcitxLightUI*) menu->priv; int length = utarray_len(&menu->shell); if (index == 0) { } else if (index == length - 1) /* Exit */ { FcitxInstanceEnd(lightui->owner); } else if (index == length - 2) /* Configuration */ { pid_t id; id = fork(); if (id < 0) FcitxLog(ERROR, _("Unable to create process")); else if (id == 0) { id = fork(); if (id < 0) { FcitxLog(ERROR, _("Unable to create process")); exit(1); } else if (id > 0) exit(0); else { execl(BINDIR "/fcitx-configtool", "fcitx-configtool", NULL); exit(0); } } } return true; }
void FcitxNotificationItemUpdateIMList(void* arg) { DBusMessage* msg = dbus_message_new_signal(NOTIFICATION_ITEM_DEFAULT_OBJ, NOTIFICATION_ITEM_DBUS_IFACE, "NewStatus"); if (msg) { const char* active = "Active"; dbus_message_append_args(msg, DBUS_TYPE_STRING, &active, DBUS_TYPE_INVALID); #if 0 FcitxNotificationItem* notificationitem = (FcitxNotificationItem*) arg; dbus_message_iter_append_basic(iter, DBUS_TYPE_STRING, &active); const char* active = "Active"; const char* passive = "Passive"; UT_array* imes = FcitxInstanceGetIMEs(notificationitem->owner); const char* status = (utarray_len(imes) > 1) ? active : passive; dbus_message_append_args(msg, DBUS_TYPE_STRING, &status, DBUS_TYPE_INVALID); dbus_connection_send(notificationitem->conn, msg, NULL); dbus_message_unref(msg); #endif } }
boolean MainMenuAction(FcitxUIMenu* menu, int index) { FcitxClassicUI* classicui = (FcitxClassicUI*) menu->priv; int length = utarray_len(&menu->shell); if (index == 0) { DisplayAboutWindow(classicui->mainWindow->owner->aboutWindow); } else if (index == 1) { FILE* p = popen("xdg-open http://fcitx.github.com/handbook/ &", "r"); if (p) pclose(p); else FcitxLog(ERROR, _("Unable to create process")); } else if (index == length - 1) { /* Exit */ FcitxInstanceEnd(classicui->owner); } else if (index == length - 2) { /* Configuration */ FILE* p = popen(BINDIR "/fcitx-configtool &", "r"); if (p) pclose(p); else FcitxLog(ERROR, _("Unable to create process")); } return true; }
device_consistency_signature_list *device_consistency_signature_list_copy(const device_consistency_signature_list *list) { int result = 0; device_consistency_signature_list *result_list = 0; unsigned int size; unsigned int i; device_consistency_signature **p; result_list = device_consistency_signature_list_alloc(); if(!result_list) { result = SG_ERR_NOMEM; goto complete; } size = utarray_len(list->values); utarray_reserve(result_list->values, size); for (i = 0; i < size; i++) { p = (device_consistency_signature **)utarray_eltptr(list->values, i); result = device_consistency_signature_list_push_back(result_list, *p); if(result < 0) { goto complete; } } complete: if(result < 0) { if(result_list) { device_consistency_signature_list_free(result_list); } return 0; } else { return result_list; } }
/** *返回鼠标指向的菜单在menu中是第多少项 */ int SelectShellIndex(XlibMenu * menu, int x, int y, int* offseth) { FcitxXlibWindow* window = (FcitxXlibWindow*) menu; int i; int contentX = window->contentX; int contentY = window->contentY; if (x < contentX) return -1; for (i = 0; i < utarray_len(&menu->menushell->shell); i++) { if (GetMenuItem(menu->menushell, i)->type == MENUTYPE_SIMPLE || GetMenuItem(menu->menushell, i)->type == MENUTYPE_SUBMENU) { if (y > contentY + 1 && y < contentY + 6 + menu->fontheight - 1) { if (offseth) *offseth = contentY; return i; } contentY = contentY + 6 + menu->fontheight; } else if (GetMenuItem(menu->menushell, i)->type == MENUTYPE_DIVLINE) { contentY += 5; } } return -1; }
/* Runtime Error */ void postorderInterative(struct TreeNode* node, UT_array* v) { UT_array* stk; utarray_new(stk, &ut_ptr_icd); utarray_reserve(stk, 8); struct TreeNode* pre = NULL; while (utarray_len(stk) > 0 || node != NULL) { if (node != NULL) { utarray_push_back(stk, node); node = node->left; } else { struct TreeNode* tmp = utarray_back(stk); if (tmp->right != NULL && pre != tmp->right) { node = tmp->right; } else { utarray_pop_back(stk); utarray_push_back(v, &tmp->val); pre = tmp; } } } utarray_free(stk); }
static void overlord_apply_deferred_rules(struct zsession *sess) { if (utarray_len(&sess->client->deferred_rules)) { struct zcrules parsed_rules; uint64_t curr_clock = zclock(false); pthread_spin_lock(&sess->client->lock); crules_init(&parsed_rules); while (utarray_back(&sess->client->deferred_rules)) { struct zrule_deferred *rule = *(struct zrule_deferred **) utarray_back(&sess->client->deferred_rules); if (rule->when > curr_clock) { break; } if (0 != crules_parse(&parsed_rules, rule->rule)) { zero_syslog(LOG_INFO, "Failed to parse deferred rule '%s' for client %s", rule->rule, ipv4_to_str(htonl(sess->ip))); } else { zero_syslog(LOG_INFO, "Applying deferred rule '%s' for client %s", rule->rule, ipv4_to_str(htonl(sess->ip))); } free(rule->rule); free(rule); utarray_pop_back(&sess->client->deferred_rules); } pthread_spin_unlock(&sess->client->lock); client_apply_rules(sess->client, &parsed_rules); crules_free(&parsed_rules); } }
FCITX_EXPORT_API boolean FcitxInstanceLoadFrontend(FcitxInstance* instance) { UT_array* addons = &instance->addons; UT_array* frontends = &instance->frontends; FcitxAddon *addon; int frontendindex = 0; utarray_clear(frontends); for (addon = (FcitxAddon *) utarray_front(addons); addon != NULL; addon = (FcitxAddon *) utarray_next(addons, addon)) { if (addon->bEnabled && addon->category == AC_FRONTEND) { char *modulePath; switch (addon->type) { case AT_SHAREDLIBRARY: { FILE *fp = FcitxXDGGetLibFile(addon->library, "r", &modulePath); void *handle; FcitxFrontend* frontend; if (!fp) break; fclose(fp); handle = dlopen(modulePath, RTLD_LAZY | RTLD_GLOBAL); if (!handle) { FcitxLog(ERROR, _("Frontend: open %s fail %s") , modulePath , dlerror()); break; } if (!CheckABIVersion(handle)) { FcitxLog(ERROR, "%s ABI Version Error", addon->name); dlclose(handle); break; } frontend = dlsym(handle, "frontend"); if (!frontend || !frontend->Create) { FcitxLog(ERROR, _("Frontend: bad frontend")); dlclose(handle); break; } if ((addon->addonInstance = frontend->Create(instance, frontendindex)) == NULL) { dlclose(handle); break; } addon->frontend = frontend; frontendindex ++; utarray_push_back(frontends, &addon); } break; default: break; } free(modulePath); } } if (utarray_len(&instance->frontends) <= 0) { FcitxLog(ERROR, _("No available frontend")); return false; } return true; }
void _fcitx_compose_table_parse_sequence(FcitxComposeTable* table, const char* line) { // we are interested in the lines with the following format: // <Multi_key> <numbersign> <S> : "♬" U266c # BEAMED SIXTEENTH NOTE const char* colon; if (!(colon = strchr(line, ':'))) { return; } uint32_t unicode; const char* quote; if (!(quote = strchr(colon, '"'))) { return; } if (quote[1] == '\\' && fcitx_utils_isdigit(quote[2])) { int base = 8; const char* start = quote + 2; if (quote[3] == 'x') { base = 16; start = quote + 3; } const char* quote2; if (!(quote2 = strrchr(quote + 3, '"'))) { return; } if (quote2 <= start) { return; } char* strDigit = strndup(start, quote2 - start); long unsigned int num = strtoul(strDigit, NULL, base); free(strDigit); unicode = fcitx_keysym_to_unicode((FcitxKeySym) num); } else { unicode = fcitx_utf8_get_char_validated(quote + 1, FCITX_UTF8_MAX_LENGTH); } FcitxStringList* keys = fcitx_utils_string_list_new(); const char* key = line; while (true) { while (key < colon && *key != '<') { key ++; } if (*key != '<') { break; } const char *start = key + 1; key = start; while (key < colon && *key != '>') { key ++; } if (*key != '>') { break; } const char *end = key; if (end == start) { continue; } fcitx_utils_string_list_append_len(keys, start, end - start); } FcitxComposeTableElement element; element.value = unicode; // Convert to X11 keysym for (uint i = 0; i < FCITX_KEYSEQUENCE_MAX_LEN; i++) { if (i < utarray_len(keys)) { char** key = utarray_eltptr(keys, i); char* keystr = *key; if (strcmp(keystr, "dead_inverted_breve") == 0) { keystr = "dead_invertedbreve"; } else if (strcmp(keystr, "dead_double_grave") == 0) { keystr = "dead_doublegrave"; } element.keys[i] = fcitx_keysym_from_string(keystr); } else { element.keys[i] = FcitxKey_None; } } fcitx_utils_string_list_free(keys); utarray_push_back(table->composeTable, &element); }
void* RunInstance(void* arg) { FcitxInstance* instance = (FcitxInstance*) arg; instance->initialized = true; int64_t curtime = 0; while (1) { FcitxAddon** pmodule; uint8_t signo = 0; while (read(instance->fd, &signo, sizeof(char)) > 0) { if (signo == SIGINT || signo == SIGTERM || signo == SIGQUIT) FcitxInstanceEnd(instance); else if (signo == SIGHUP) fcitx_utils_launch_restart(); else if (signo == SIGUSR1) FcitxInstanceReloadConfig(instance); } do { instance->uiflag = UI_NONE; for (pmodule = (FcitxAddon**) utarray_front(&instance->eventmodules); pmodule != NULL; pmodule = (FcitxAddon**) utarray_next(&instance->eventmodules, pmodule)) { FcitxModule* module = (*pmodule)->module; module->ProcessEvent((*pmodule)->addonInstance); } struct timeval current_time; gettimeofday(¤t_time, NULL); curtime = (current_time.tv_sec * 1000LL) + (current_time.tv_usec / 1000LL); int idx = 0; while(idx < utarray_len(&instance->timeout)) { TimeoutItem* ti = (TimeoutItem*) utarray_eltptr(&instance->timeout, idx); uint64_t id = ti->idx; if (ti->time + ti->milli <= curtime) { ti->callback(ti->arg); ti = (TimeoutItem*) utarray_eltptr(&instance->timeout, idx); /* faster remove */ if (ti && ti->idx == id) utarray_remove_quick(&instance->timeout, idx); else { FcitxInstanceRemoveTimeoutById(instance, id); idx = 0; } } else { idx++; } } if (instance->uiflag & UI_MOVE) FcitxUIMoveInputWindowReal(instance); if (instance->uiflag & UI_UPDATE) FcitxUIUpdateInputWindowReal(instance); } while (instance->uiflag != UI_NONE); FD_ZERO(&instance->rfds); FD_ZERO(&instance->wfds); FD_ZERO(&instance->efds); instance->maxfd = 0; if (instance->fd > 0) { instance->maxfd = instance->fd; FD_SET(instance->fd, &instance->rfds); } for (pmodule = (FcitxAddon**) utarray_front(&instance->eventmodules); pmodule != NULL; pmodule = (FcitxAddon**) utarray_next(&instance->eventmodules, pmodule)) { FcitxModule* module = (*pmodule)->module; module->SetFD((*pmodule)->addonInstance); } if (instance->maxfd == 0) break; struct timeval tval; struct timeval* ptval = NULL; if (utarray_len(&instance->timeout) != 0) { long int min_time = LONG_MAX; TimeoutItem* ti; for (ti = (TimeoutItem*) utarray_front(&instance->timeout); ti != NULL; ti = (TimeoutItem*) utarray_next(&instance->timeout, ti)) { if (ti->time + ti->milli - curtime < min_time) { min_time = ti->time + ti->milli - curtime; } } tval.tv_usec = (min_time % 1000) * 1000; tval.tv_sec = min_time / 1000; ptval = &tval; } select(instance->maxfd + 1, &instance->rfds, &instance->wfds, &instance->efds, ptval); } return NULL; }
int main(int argc, char *argv[]) { zmq_rcvmore_t more; size_t more_sz = sizeof(more); char *exe = argv[0], *filter = ""; int part_num,opt,rc=-1; void *msg_data, *sp, *set=NULL; char **endpoint; UT_array *endpoints; size_t msg_len; zmq_msg_t part; utarray_new(endpoints,&ut_str_icd); while ( (opt = getopt(argc, argv, "sd:f:v+")) != -1) { switch (opt) { case 'v': verbose++; break; case 's': pull_mode++; break; case 'd': dir=strdup(optarg); break; case 'f': remotes_file=strdup(optarg); break; default: usage(exe); break; } } if (!dir) usage(exe); sp = kv_spoolwriter_new(dir); if (!sp) usage(exe); set = kv_set_new(); /* connect socket to each publisher. yes, zeromq lets you connect n times */ if ( !(context = zmq_init(1))) goto done; if ( !(socket = zmq_socket(context, pull_mode?ZMQ_PULL:ZMQ_SUB))) goto done; if (remotes_file) if (read_lines(remotes_file,endpoints)) goto done; while (optind < argc) utarray_push_back(endpoints,&argv[optind++]); endpoint=NULL; if (utarray_len(endpoints) == 0) usage(argv[0]); while ( (endpoint=(char**)utarray_next(endpoints,endpoint))) { if (verbose) fprintf(stderr,"connecting to %s\n", *endpoint); if (zmq_connect(socket, *endpoint)) goto done; } if (!pull_mode) { if (zmq_setsockopt(socket, ZMQ_SUBSCRIBE, filter, strlen(filter))) goto done; } while(1) { /* receive a multi-part message */ part_num=1; do { if ( (rc= zmq_msg_init(&part))) goto done; if ( ((rc= zmq_recvmsg(socket, &part, 0)) == -1) || ((rc= zmq_getsockopt(socket, ZMQ_RCVMORE, &more,&more_sz)) != 0)) { zmq_msg_close(&part); goto done; } msg_data = zmq_msg_data(&part); msg_len = zmq_msg_size(&part); switch(part_num) { /* part 1 has serialized frame */ case 1: if (json_to_frame(sp,set,msg_data,msg_len)) goto done; break; default: assert(0); } zmq_msg_close(&part); part_num++; } while(more); } rc = 0; /* not reached TODO under clean shutdown on signal */ done: if (rc) fprintf(stderr,"%s: %s\n", exe, zmq_strerror(errno)); if(socket) zmq_close(socket); if(context) zmq_term(context); kv_spoolwriter_free(sp); if (set) kv_set_free(set); utarray_free(endpoints); return rc; }
int main(int argc, char *argv[]) { UT_array *dlls = NULL; pid_t pid = -1; char *wndtitle = NULL, *wndclass = NULL; int flags = 0; arg0 = argv[0]; if (isatty(fileno(stderr))) opts.color = 1; utarray_new(dlls, &ut_str_icd); while (optind < argc) { int opt; if((opt = getopt(argc, argv, "ap:w:c:f:hvl:L:x")) != -1) { switch(opt) { char *endptr; case 'L': if (chdir(optarg) == -1) die("Invalid path -L%s", optarg); break; case 'l': { char *dll = concat(DLL_PREFIX, optarg, DLL_SUFFIX, 0); if (access(dll, F_OK) == -1) { warn("File '%s' not found", dll); opts.failed = 1; continue; } utarray_push_back(dlls, &dll); } break; case 'f': /* file name */ pid = pid_byname(optarg); if (pid < 0) die("No matching process found."); break; case 'w': /* window title */ wndtitle = optarg; break; case 'c': /* window class */ wndclass = optarg; break; case 'p': /* process id */ if (*optarg == '-' || !(pid = strtoul(optarg, &endptr, 0)) || optarg == endptr) { warn("%s: argument must be process or job ID", optarg); } break; case 'a': /* await */ opts.await = 1; break; case 'x': flags = LADE_CRASH; opts.noarg = 1; break; case 'h': return print_usage(true); case 'v': opts.verbose = 1; break; default: break; } } else { char *dll = argv[optind++]; if (access(dll, F_OK) == -1) { warn("File '%s' not found", dll); opts.failed = 1; continue; } utarray_push_back(dlls, &dll); } } if (wndclass || wndtitle) pid = pid_bywindow(wndclass, wndtitle); if (opts.noarg) return lade(pid, NULL, flags) != NULL; else if (!utarray_len(dlls)) die("%s: No input files", arg0); for(const char **dll = utarray_front(dlls); dll; dll = utarray_next(dlls, dll)) { lade_t *h = lade(pid, *dll, flags); if (!h) die("Injecting %ld with %s failed.", (long)pid, *dll); } if (opts.await && pid == -1) { puts("Waiting indefinitely... Press ^C to exit."); for (;;) pause(); } return EXIT_SUCCESS; }
static void py_enhance_load_py(PinyinEnhance *pyenhance) { UT_array *array = &pyenhance->py_list; if (array->icd) return; utarray_init(array, fcitx_ptr_icd); FILE *fp; char *fname; fname = fcitx_utils_get_fcitx_path_with_filename( "pkgdatadir", "py-enhance/"PY_TABLE_FILE); fp = fopen(fname, "r"); free(fname); if (fp) { FcitxMemoryPool *pool = pyenhance->static_pool; char buff[UTF8_MAX_LENGTH + 1]; int buff_size = 33; int8_t *list_buff = malloc(buff_size); size_t res; int8_t word_l; int8_t count; int8_t py_size; int i; int8_t *py_list; int8_t *tmp; /** * Format: * int8_t word_l; * char word[word_l]; * int8_t count; * int8_t py[count][3]; **/ while (true) { res = fread(&word_l, 1, 1, fp); if (!res || word_l < 0 || word_l > UTF8_MAX_LENGTH) break; res = fread(buff, word_l + 1, 1, fp); if (!res) break; count = buff[word_l]; if (count < 0) break; if (count == 0) continue; py_size = count * 3; if (buff_size < py_size) { buff_size = py_size; list_buff = realloc(list_buff, buff_size); } res = fread(list_buff, py_size, 1, fp); if (!res) break; py_list = fcitx_memory_pool_alloc(pool, word_l + py_size + 3); py_list[0] = word_l + 1; py_list++; memcpy(py_list, buff, word_l); tmp = py_list + word_l; *tmp = '\0'; tmp++; *tmp = count; memcpy(tmp + 1, list_buff, py_size); for (i = utarray_len(array) - 1;i >= 0;i--) { if (strcmp(*(char**)_utarray_eltptr(array, i), (char*)py_list) < 0) { break; } } utarray_insert(array, &py_list, i + 1); } free(list_buff); fclose(fp); } }
FCITX_EXPORT_API FcitxStandardPathFile* fcitx_standard_path_locate(FcitxStandardPath* sp, FcitxStandardPathType type, const char* path, uint32_t flag) { if (path[0] == '/') { const char* flags = (flag & FSPFT_Append) ? "a" : (flag & FSPFT_Writable ? "w" : "r"); FILE* fp = fopen(path, flags); if (!fp) { return NULL; } FcitxStandardPathFile* result = fcitx_utils_newv(FcitxStandardPathFile, 2); result[0].fp = fp; result[0].path = fcitx_utils_strdup(path); return result; } char* firstDir = NULL; FcitxStringList* list = NULL; fcitx_standard_path_get(sp, type, &firstDir, &list); if (!firstDir && !list) { return NULL; } // if we don't write and there is a list bool checkList = (!(flag & FSPFT_Write) && list); FcitxStandardPathFile fileFirst = { NULL, NULL }; if (firstDir) { fileFirst = fcitx_standard_path_try_open(firstDir, path, flag); } FcitxStandardPathFile* result = NULL; if (!checkList) { if (!checkList && !fileFirst.fp) { return NULL; } result = fcitx_utils_newv(FcitxStandardPathFile, 2); result[0] = fileFirst; } else { size_t idx = 0; size_t resultSize = (flag & FSPFT_LocateAll) ? (1 + (fileFirst.fp ? 1 : 0) + utarray_len(list)) : 2; if (fileFirst.fp) { // alloc on required result = fcitx_utils_newv(FcitxStandardPathFile, resultSize); result[idx] = fileFirst; idx++; } if (!(flag & FSPFT_Write) && list) { utarray_foreach(dir, list, char*) { if (idx == 1 && !(flag & FSPFT_LocateAll)) { break; } FcitxStandardPathFile file = fcitx_standard_path_try_open(*dir, path, flag); if (file.fp) { // alloc on required if (!result) { result = fcitx_utils_newv(FcitxStandardPathFile, resultSize); } result[idx] = file; idx++; } } } }
/* * Whether the string matches the given glob pattern */ EDITORCONFIG_LOCAL int ec_glob(const char *pattern, const char *string) { size_t i; int_pair * p; char * c; char pcre_str[2 * PATTERN_MAX] = "^"; char * p_pcre; int brace_level = 0; bool is_in_bracket = false; const char * error_msg; int erroffset; pcre * re; int rc; int * pcre_result; size_t pcre_result_len; char l_pattern[2 * PATTERN_MAX]; int pattern_length = strlen(pattern); bool are_brace_paired; UT_array * nums; /* number ranges */ int ret = 0; strcpy(l_pattern, pattern); p_pcre = pcre_str + 1; { int left_count = 0; int right_count = 0; for (c = l_pattern; *c; ++ c) { if (*c == '\\' && *(c+1) != '\0') { ++ c; continue; } if (*c == '}') ++ right_count; if (*c == '{') ++ left_count; } are_brace_paired = (right_count == left_count); } /* used to search for {num1..num2} case */ re = pcre_compile("^\\{[\\+\\-]?\\d+\\.\\.[\\+\\-]?\\d+\\}$", 0, &error_msg, &erroffset, NULL); if (!re) /* failed to compile */ return -1; utarray_new(nums, &ut_int_pair_icd); for (c = l_pattern; *c; ++ c) { switch (*c) { case '\\': /* also skip the next one */ if (*(c+1) != '\0') { *(p_pcre ++) = *(c++); *(p_pcre ++) = *c; } else STRING_CAT(p_pcre, "\\\\"); break; case '?': *(p_pcre ++) = '.'; break; case '*': if (*(c+1) == '*') /* case of ** */ { STRING_CAT(p_pcre, ".*"); ++ c; } else /* case of * */ STRING_CAT(p_pcre, "[^\\/]*"); break; case '[': if (is_in_bracket) /* inside brackets, we really mean bracket */ { STRING_CAT(p_pcre, "\\["); break; } { /* check whether we have slash within the bracket */ bool has_slash = false; char * cc; for (cc = c; *cc && *cc != ']'; ++ cc) { if (*cc == '\\' && *(cc+1) != '\0') { ++ cc; continue; } if (*cc == '/') { has_slash = true; break; } } /* if we have slash in the brackets, just do it literally */ if (has_slash) { char * right_bracket = strchr(c, ']'); strcat(p_pcre, "\\"); strncat(p_pcre, c, right_bracket - c); strcat(p_pcre, "\\]"); p_pcre += strlen(p_pcre); c = right_bracket; break; } } is_in_bracket = true; if (*(c+1) == '!') /* case of [!...] */ { STRING_CAT(p_pcre, "[^"); ++ c; } else *(p_pcre ++) = '['; break; case ']': is_in_bracket = false; *(p_pcre ++) = *c; break; case '-': if (is_in_bracket) /* in brackets, - indicates range */ *(p_pcre ++) = *c; else STRING_CAT(p_pcre, "\\-"); break; case '{': if (!are_brace_paired) { STRING_CAT(p_pcre, "\\{"); break; } /* Check the case of {single}, where single can be empty */ { char * cc; bool is_single = true; for (cc = c + 1; *cc != '\0' && *cc != '}'; ++ cc) { if (*cc == '\\' && *(cc+1) != '\0') { ++ cc; continue; } if (*cc == ',') { is_single = false; break; } } if (*cc == '\0') is_single = false; if (is_single) /* escape the { and the corresponding } */ { const char * double_dots; int_pair pair; int pcre_res[3]; /* Check the case of {num1..num2} */ rc = pcre_exec(re, NULL, c, (int) (cc - c + 1), 0, 0, pcre_res, 3); if (rc < 0) /* not {num1..num2} case */ { STRING_CAT(p_pcre, "\\{"); memmove(cc+1, cc, strlen(cc) + 1); *cc = '\\'; break; } /* Get the range */ double_dots = strstr(c, ".."); pair.num1 = atoi(c + 1); pair.num2 = atoi(double_dots + 2); utarray_push_back(nums, &pair); STRING_CAT(p_pcre, "([\\+\\-]?\\d+)"); c = cc; break; } } ++ brace_level; STRING_CAT(p_pcre, "(?:"); break; case '}': if (!are_brace_paired) { STRING_CAT(p_pcre, "\\}"); break; } -- brace_level; *(p_pcre ++) = ')'; break; case ',': if (brace_level > 0) /* , inside {...} */ *(p_pcre ++) = '|'; else STRING_CAT(p_pcre, "\\,"); break; case '/': // /**/ case, match both single / and /anything/ if (!strncmp(c, "/**/", 4)) { STRING_CAT(p_pcre, "(\\/|\\/.*\\/)"); c += 3; } else STRING_CAT(p_pcre, "\\/"); break; default: if (!isalnum(*c)) *(p_pcre ++) = '\\'; *(p_pcre ++) = *c; } } *(p_pcre ++) = '$'; pcre_free(re); /* ^\\d+\\.\\.\\d+$ */ re = pcre_compile(pcre_str, 0, &error_msg, &erroffset, NULL); if (!re) /* failed to compile */ return -1; pcre_result_len = 3 * (utarray_len(nums) + 1); pcre_result = (int *) calloc(pcre_result_len, sizeof(int_pair)); rc = pcre_exec(re, NULL, string, (int) strlen(string), 0, 0, pcre_result, pcre_result_len); if (rc < 0) /* failed to match */ { int ret; if (rc == PCRE_ERROR_NOMATCH) ret = EC_GLOB_NOMATCH; else ret = rc; pcre_free(re); free(pcre_result); utarray_free(nums); return ret; } /* Whether the numbers are in the desired range? */ for(p = (int_pair *) utarray_front(nums), i = 1; p; ++ i, p = (int_pair *) utarray_next(nums, p)) { const char * substring_start = string + pcre_result[2 * i]; size_t substring_length = pcre_result[2 * i + 1] - pcre_result[2 * i]; char * num_string; int num; /* we don't consider 0digits such as 010 as matched */ if (*substring_start == '0') break; num_string = strndup(substring_start, substring_length); num = atoi(num_string); free(num_string); if (num < p->num1 || num > p->num2) /* not matched */ break; } if (p != NULL) /* numbers not matched */ ret = EC_GLOB_NOMATCH; pcre_free(re); free(pcre_result); utarray_free(nums); return ret; }
FCITX_EXPORT_API int FcitxCandidateWordGetListSize(FcitxCandidateWordList* candList) { return utarray_len(&candList->candWords); }
void test_string() { const char *test = TEST_STR; FcitxStringList* list = fcitx_utils_string_split(test, ","); assert(utarray_len(list) == 4); assert(fcitx_utils_string_list_contains(list, "a")); assert(fcitx_utils_string_list_contains(list, "b")); assert(fcitx_utils_string_list_contains(list, "c")); assert(fcitx_utils_string_list_contains(list, "d")); assert(!fcitx_utils_string_list_contains(list, "e")); char* join = fcitx_utils_string_list_join(list, ','); assert(strcmp(join, test) == 0); fcitx_utils_string_list_append_split(list, TEST_STR, "\n"); fcitx_utils_string_list_printf_append(list, "%s", TEST_STR); char *join2 = fcitx_utils_string_list_join(list, ','); assert(strcmp(join2, TEST_STR","TEST_STR","TEST_STR) == 0); char* cat = NULL; fcitx_utils_alloc_cat_str(cat, join, ",e"); assert(strcmp(cat, TEST_STR",e") == 0); fcitx_utils_set_cat_str(cat, join, ",e,", join); assert(strcmp(cat, TEST_STR",e,"TEST_STR) == 0); join = fcitx_utils_set_str(join, join2); assert(strcmp(join, join2) == 0); free(cat); free(join); free(join2); fcitx_utils_string_list_free(list); list = fcitx_utils_string_split_full("a b", " ", false); assert(utarray_len(list) == 2); fcitx_utils_string_list_free(list); char localcat[20]; const char *array[] = {"a", ",b", ",c", ",d"}; fcitx_utils_cat_str_simple(localcat, 4, array); assert(strcmp(localcat, test) == 0); char localcat2[6]; fcitx_utils_cat_str_simple_with_len(localcat2, 4, 4, array); assert(strcmp(localcat2, "a,b") == 0); fcitx_utils_cat_str_simple_with_len(localcat2, 5, 4, array); assert(strcmp(localcat2, "a,b,") == 0); fcitx_utils_cat_str_simple_with_len(localcat2, 6, 4, array); assert(strcmp(localcat2, "a,b,c") == 0); const char *orig = "\r78\"1\n\\\e\\3\f\a\v\'cc\td\b"; char *escape = fcitx_utils_set_escape_str(NULL, orig); assert(strcmp(escape, "\\r78\\\"1\\n\\\\\\e\\\\3\\f\\a\\v\\\'cc\\td\\b") == 0); char *back = fcitx_utils_set_unescape_str(NULL, escape); assert(strcmp(orig, back) == 0); fcitx_utils_unescape_str_inplace(escape); assert(strcmp(orig, escape) == 0); free(escape); free(back); char* replace_result = fcitx_utils_string_replace("abcabc", "a", "b", true); assert(strcmp(replace_result, "bbcbbc") == 0); free(replace_result); #define REPEAT 2049 char largeReplace[3 * REPEAT + 1]; char largeReplaceCorrect[REPEAT + 1]; char largeReplaceCorrect2[4 * REPEAT + 1]; int i = 0, j = 0, k = 0; for (int n = 0; n < REPEAT; n ++) { largeReplace[i++] = 'a'; largeReplace[i++] = 'b'; largeReplace[i++] = 'c'; largeReplaceCorrect[j++] = 'e'; largeReplaceCorrect2[k++] = 'a'; largeReplaceCorrect2[k++] = 'b'; largeReplaceCorrect2[k++] = 'c'; largeReplaceCorrect2[k++] = 'd'; } largeReplace[i] = '\0'; largeReplaceCorrect[j] = '\0'; largeReplaceCorrect2[k] = '\0'; replace_result = fcitx_utils_string_replace(largeReplace, "abc", "e", true); assert(strcmp(replace_result, largeReplaceCorrect) == 0); char* replace_result2 = fcitx_utils_string_replace(replace_result, "e", "abcd", true); free(replace_result); assert(strcmp(replace_result2, largeReplaceCorrect2) == 0); free(replace_result2); assert(fcitx_utils_string_replace(largeReplace, "de", "bcd", true) == NULL); }
void* RunInstance(void* arg) { FcitxInstance* instance = (FcitxInstance*) arg; FcitxAddonsInit(&instance->addons); FcitxInstanceInitIM(instance); FcitxInstanceInitNoPreeditApps(instance); FcitxFrontendsInit(&instance->frontends); InitFcitxModules(&instance->modules); InitFcitxModules(&instance->eventmodules); utarray_init(&instance->uistats, &stat_icd); utarray_init(&instance->uicompstats, &compstat_icd); utarray_init(&instance->uimenus, fcitx_ptr_icd); utarray_init(&instance->timeout, &timeout_icd); utarray_init(&instance->icdata, &icdata_icd); instance->input = FcitxInputStateCreate(); instance->config = fcitx_utils_malloc0(sizeof(FcitxGlobalConfig)); instance->profile = fcitx_utils_malloc0(sizeof(FcitxProfile)); instance->globalIMName = strdup(""); if (instance->fd >= 0) { fcntl(instance->fd, F_SETFL, O_NONBLOCK); } else { instance->fd = -1; } if (!FcitxGlobalConfigLoad(instance->config)) goto error_exit; FcitxCandidateWordSetPageSize(instance->input->candList, instance->config->iMaxCandWord); int overrideDelay = instance->overrideDelay; if (overrideDelay < 0) overrideDelay = instance->config->iDelayStart; if (overrideDelay > 0) sleep(overrideDelay); instance->timeStart = time(NULL); instance->globalState = instance->config->defaultIMState; instance->totaltime = 0; FcitxInitThread(instance); if (!FcitxProfileLoad(instance->profile, instance)) goto error_exit; if (FcitxAddonGetConfigDesc() == NULL) goto error_exit; if (GetIMConfigDesc() == NULL) goto error_exit; FcitxAddonsLoad(&instance->addons); FcitxInstanceFillAddonOwner(instance, NULL); FcitxInstanceResolveAddonDependency(instance); FcitxInstanceInitBuiltInHotkey(instance); FcitxInstanceInitBuiltContext(instance); FcitxModuleLoad(instance); if (instance->loadingFatalError) return NULL; if (!FcitxInstanceLoadAllIM(instance)) { goto error_exit; } FcitxInstanceInitIMMenu(instance); FcitxUIRegisterMenu(instance, &instance->imMenu); FcitxUIRegisterStatus(instance, instance, "remind", instance->profile->bUseRemind ? _("Use remind") : _("No remind"), _("Toggle Remind"), ToggleRemindState, GetRemindEnabled); FcitxUISetStatusVisable(instance, "remind", false); FcitxUILoad(instance); instance->iIMIndex = FcitxInstanceGetIMIndexByName(instance, instance->profile->imName); if (instance->iIMIndex < 0) { instance->iIMIndex = 0; } FcitxInstanceSwitchIMByIndex(instance, instance->iIMIndex); if (!FcitxInstanceLoadFrontend(instance)) { goto error_exit; } /* fcitx is running in a standalone thread or not */ if (instance->sem) { sem_post(&instance->notifySem); sem_wait(&instance->startUpSem); } else { instance->initialized = true; } uint64_t curtime = 0; while (1) { FcitxAddon** pmodule; uint8_t signo = 0; if (instance->fd >= 0) { while (read(instance->fd, &signo, sizeof(char)) > 0) { if (signo == SIGINT || signo == SIGTERM || signo == SIGQUIT || signo == SIGXCPU) FcitxInstanceEnd(instance); else if (signo == SIGHUP) FcitxInstanceRestart(instance); else if (signo == SIGUSR1) FcitxInstanceReloadConfig(instance); } } do { instance->eventflag &= (~FEF_PROCESS_EVENT_MASK); for (pmodule = (FcitxAddon**) utarray_front(&instance->eventmodules); pmodule != NULL; pmodule = (FcitxAddon**) utarray_next(&instance->eventmodules, pmodule)) { FcitxModule* module = (*pmodule)->module; module->ProcessEvent((*pmodule)->addonInstance); } struct timeval current_time; gettimeofday(¤t_time, NULL); curtime = (current_time.tv_sec * 1000LL) + (current_time.tv_usec / 1000LL); unsigned int idx = 0; while(idx < utarray_len(&instance->timeout)) { TimeoutItem* ti = (TimeoutItem*) utarray_eltptr(&instance->timeout, idx); uint64_t id = ti->idx; if (ti->time + ti->milli <= curtime) { ti->callback(ti->arg); ti = (TimeoutItem*) utarray_eltptr(&instance->timeout, idx); /* faster remove */ if (ti && ti->idx == id) utarray_remove_quick(&instance->timeout, idx); else { FcitxInstanceRemoveTimeoutById(instance, id); idx = 0; } } else { idx++; } } if (instance->eventflag & FEF_UI_MOVE) FcitxUIMoveInputWindowReal(instance); if (instance->eventflag & FEF_UI_UPDATE) FcitxUIUpdateInputWindowReal(instance); } while ((instance->eventflag & FEF_PROCESS_EVENT_MASK) != FEF_NONE); setjmp(FcitxRecover); if (instance->destroy || instance->restart) { FcitxInstanceRealEnd(instance); break; } if (instance->eventflag & FEF_RELOAD_ADDON) { instance->eventflag &= ~(FEF_RELOAD_ADDON); FcitxInstanceReloadAddon(instance); } FD_ZERO(&instance->rfds); FD_ZERO(&instance->wfds); FD_ZERO(&instance->efds); instance->maxfd = 0; if (instance->fd > 0) { instance->maxfd = instance->fd; FD_SET(instance->fd, &instance->rfds); } for (pmodule = (FcitxAddon**) utarray_front(&instance->eventmodules); pmodule != NULL; pmodule = (FcitxAddon**) utarray_next(&instance->eventmodules, pmodule)) { FcitxModule* module = (*pmodule)->module; module->SetFD((*pmodule)->addonInstance); } if (instance->maxfd == 0) break; struct timeval tval; struct timeval* ptval = NULL; if (utarray_len(&instance->timeout) != 0) { unsigned long int min_time = LONG_MAX; TimeoutItem* ti; for (ti = (TimeoutItem*)utarray_front(&instance->timeout);ti; ti = (TimeoutItem*)utarray_next(&instance->timeout, ti)) { if (ti->time + ti->milli - curtime < min_time) { min_time = ti->time + ti->milli - curtime; } } tval.tv_usec = (min_time % 1000) * 1000; tval.tv_sec = min_time / 1000; ptval = &tval; } select(instance->maxfd + 1, &instance->rfds, &instance->wfds, &instance->efds, ptval); } if (instance->restart) { fcitx_utils_restart_in_place(); } return NULL; error_exit: sem_post(&instance->startUpSem); FcitxInstanceEnd(instance); return NULL; }