// creates and returns a range *object by parsing a string // with format "%f:%f:%f" range_t *range_init_from_string(const char *st) { // create a gstring from st GString *gst = g_string_new(st); // split the gstring GPtrArray *tokens = g_string_split(gst, ':'); assert(tokens->len == 3); // parse the values GString *s = g_ptr_array_index(tokens, 0); double start = atof(s->str); g_string_free(s, TRUE); s = g_ptr_array_index(tokens, 1); double stop = atof(s->str); g_string_free(s, TRUE); s = g_ptr_array_index(tokens, 2); double step = atof(s->str); g_string_free(s, TRUE); // free the pointer array (strings have been freed) g_ptr_array_free(tokens, TRUE); // free the gstring g_string_free(gst, TRUE); return range_init(start, stop, step); }
END_TEST START_TEST(test_g_list_slices_u64) { unsigned i=0; unsigned j=98; unsigned s=11; uint64_t *l; GList *list = NULL; GList *sub = NULL; for (i=0; i< j; i++) { l = g_new0(uint64_t,1); *l = i; list = g_list_append(list, l); } list = g_list_slices_u64(list, s); list = g_list_first(list); fail_unless(g_list_length(list)==9, "number of slices incorrect"); sub = g_string_split(g_string_new((gchar *)list->data), ","); fail_unless(g_list_length(sub)==s,"Slice length incorrect"); g_list_foreach(list,(GFunc)g_free,NULL); g_list_foreach(sub,(GFunc)g_free,NULL); i=0; j=17; s=100; list = NULL; sub = NULL; for (i=0; i< j; i++) list = g_list_append_printf(list, "ELEM_%d", i); list = g_list_slices(list, s); list = g_list_first(list); fail_unless(g_list_length(list)==1, "number of slices incorrect [%d]", g_list_length(list)); sub = g_string_split(g_string_new((gchar *)list->data), ","); fail_unless(g_list_length(sub)==j,"Slice length incorrect"); }
/* Fills the aliases list with all existing aliases * return -2 on mem error, -1 on db-error, 0 on succeses */ GList * auth_get_known_aliases(void) { char *query; const char *fields[] = { _ldap_cfg.field_uid, NULL }; GList *aliases; GList *entlist; GString *t = g_string_new(_ldap_cfg.forw_objectclass); GList *l = g_string_split(t,","); g_string_free(t,TRUE); query = dm_ldap_get_filter('&',"objectClass",l); entlist = __auth_get_every_match(query, fields); g_free(query); TRACE(TRACE_INFO, "found %d aliases", g_list_length(entlist)); aliases = dm_ldap_ent_get_values(entlist); dm_ldap_freeresult(entlist); return aliases; }
int auth_check_user_ext(const char *address, GList **userids, GList **fwds, int checks) { int occurences = 0; u64_t id, *uid; char *endptr = NULL; char *query; const char *fields[] = { _ldap_cfg.field_nid, _ldap_cfg.field_fwdtarget[0] ? _ldap_cfg.field_fwdtarget : NULL, NULL }; char *attrvalue; GList *entlist, *fldlist, *attlist, *searchlist; if (checks > 20) { TRACE(TRACE_ERR, "too many checks. Possible loop detected."); return 0; } TRACE(TRACE_DEBUG, "checking user [%s] in alias table", address); if (strlen(_ldap_cfg.query_string)==0) { /* build a mail filter, with multiple attributes, if needed */ GString *f = g_string_new(_ldap_cfg.field_mail); searchlist = g_string_split(f,","); g_string_free(f,TRUE); GString *t = g_string_new(""); GString *q = g_string_new(""); GList *l = NULL; searchlist = g_list_first(searchlist); while(searchlist) { g_string_printf(t,"%s=%s",(char *)searchlist->data,address); l = g_list_append(l,g_strdup(t->str)); if(!g_list_next(searchlist)) break; searchlist = g_list_next(searchlist); } t = g_list_join(l,")("); g_string_printf(q,"(|(%s))", t->str); query = q->str; g_string_free(t,TRUE); g_string_free(q,FALSE); g_list_foreach(l,(GFunc)g_free,NULL); g_list_free(l); } else { int i; GString *q = g_string_new(""); for (i = 0; _ldap_cfg.query_string[i] != '\0'; i++) { if (_ldap_cfg.query_string[i]=='%' && _ldap_cfg.query_string[i+1] && _ldap_cfg.query_string[i+1]=='s') { g_string_append(q,address); i++; } else { g_string_append_c(q,_ldap_cfg.query_string[i]); } } query = q->str; g_string_free(q,FALSE); } TRACE(TRACE_DEBUG, "searching with query [%s], checks [%d]", query, checks); entlist = __auth_get_every_match(query, fields); g_free(query); if (g_list_length(entlist) < 1) { if (checks > 0) { /* found the last one, this is the deliver to * but checks needs to be bigger then 0 because * else it could be the first query failure */ id = strtoull(address, &endptr, 10); if (*endptr == 0) { /* numeric deliver-to --> this is a userid */ TRACE(TRACE_DEBUG, "adding [%llu] to userids", id); uid = g_new0(u64_t,1); *uid = id; *(GList **)userids = g_list_prepend(*(GList **)userids, uid); } else { TRACE(TRACE_DEBUG, "adding [%s] to forwards", address); *(GList **)fwds = g_list_prepend(*(GList **)fwds, g_strdup(address)); } return 1; } else { TRACE(TRACE_DEBUG, "user [%s] not in aliases table", address); dm_ldap_freeresult(entlist); return 0; } } TRACE(TRACE_DEBUG, "into checking loop"); entlist = g_list_first(entlist); while (entlist) { fldlist = g_list_first(entlist->data); while(fldlist) { attlist = g_list_first(fldlist->data); while(attlist) { attrvalue = (char *)attlist->data; occurences += auth_check_user_ext(attrvalue, userids, fwds, checks+1); if (! g_list_next(attlist)) break; attlist = g_list_next(attlist); } if (! g_list_next(fldlist)) break; fldlist = g_list_next(fldlist); } if (! g_list_next(entlist)) break; entlist = g_list_next(entlist); } dm_ldap_freeresult(entlist); return occurences; }
GTree * MailboxState_get_set(MailboxState_T M, const char *set, gboolean uid) { GTree *inset, *a, *b; GList *sets = NULL; GString *t; uint64_t lo = 0, hi = 0; gboolean error = FALSE; if (uid) inset = MailboxState_getIds(M); else inset = MailboxState_getMsn(M); a = g_tree_new_full((GCompareDataFunc)ucmpdata,NULL, (GDestroyNotify)uint64_free, (GDestroyNotify)uint64_free); b = g_tree_new_full((GCompareDataFunc)ucmpdata,NULL, (GDestroyNotify)uint64_free, (GDestroyNotify)uint64_free); if (! uid) { lo = 1; hi = MailboxState_getExists(M); } else { GList *ids = g_tree_keys(inset); if (ids) { ids = g_list_last(ids); hi = *((uint64_t *)ids->data); ids = g_list_first(ids); lo = *((uint64_t *)ids->data); g_list_free(g_list_first(ids)); } } t = g_string_new(set); sets = g_string_split(t,","); g_string_free(t,TRUE); sets = g_list_first(sets); while(sets) { uint64_t l = 0, r = 0; char *rest = (char *)sets->data; if (strlen(rest) < 1) break; if (g_tree_nnodes(inset) == 0) { // empty box if (rest[0] == '*') { uint64_t *k = mempool_pop(small_pool, sizeof(uint64_t)); uint64_t *v = mempool_pop(small_pool, sizeof(uint64_t)); *k = 1; *v = MailboxState_getUidnext(M); g_tree_insert(b, k, v); } else { if (! (l = dm_strtoull(sets->data, &rest, 10))) { error = TRUE; break; } if (rest[0]) { if (rest[0] != ':') { error = TRUE; break; } rest++; if ((rest[0] != '*') && (! dm_strtoull(rest, NULL, 10))) { error = TRUE; break; } } uint64_t *k = mempool_pop(small_pool, sizeof(uint64_t)); uint64_t *v = mempool_pop(small_pool, sizeof(uint64_t)); *k = 1; *v = MailboxState_getUidnext(M); g_tree_insert(b, k, v); } } else { if (rest[0] == '*') { l = hi; r = l; if (strlen(rest) > 1) rest++; } else { if (! (l = dm_strtoull(sets->data,&rest,10))) { error = TRUE; break; } if (l == 0xffffffff) l = hi; // outlook l = max(l,lo); r = l; } if (rest[0]==':') { if (strlen(rest)>1) rest++; if (rest[0] == '*') r = hi; else { if (! (r = dm_strtoull(rest,NULL,10))) { error = TRUE; break; } if (r == 0xffffffff) r = hi; // outlook } if (!r) break; } if (! (l && r)) break; find_range(inset, min(l,r), max(l,r), a, uid); if (g_tree_merge(b,a,IST_SUBSEARCH_OR)) { error = TRUE; TRACE(TRACE_ERR, "cannot compare null trees"); break; } } if (! g_list_next(sets)) break; sets = g_list_next(sets); } g_list_destroy(sets); if (a) g_tree_destroy(a); if (error) { g_tree_destroy(b); b = NULL; TRACE(TRACE_DEBUG, "return NULL"); } return b; }