#define _GNU_SOURCE #include #include #include #include #include #include #include bool cmp_find(const map_t *pIN needle, const map_t *pIN haystack, usize *pOUT pos) { u8* start; //TODO: Find sub-substring even if the full match fails u8* substr = memmem(start = haystack->origin, haystack->len, needle->origin, needle->len); if(!substr) return false; debug_assert(substr >= start); *pos = (usize) (substr - start); return true; } int cmp_find_many(const map_t *pIN needle, usize nhaystacks, usize sizes[pOUT nhaystacks], ...) { va_list v_haystacks; va_start(v_haystacks, sizes); const map_t* pINOUT haystack; register int rval=-1; for(usize i=0;iorigin) FATAL("haystack %lu was null or its origin was null", i); if(!cmp_find(needle, haystack, size)) { rval = (int)i; break; } } va_end(v_haystacks); return rval; } comp_multires_t* comp_match_all(map_t *pIN needle, usize nh, map_t hs[pIN nh], bool abort_on_fail) { comp_multires_t* result = malloc(sizeof(comp_multires_t) + (sizeof(struct comp_single_result) * nh)); debug_assert(result); result->all_matched = true; result->idx_first_failure = -1; result->num_results = nh; usize i; for(i =0;iaggr[i] = res; if(!res.matched) { WARN("Matching haystack %lu failed", i); result->all_matched = false; if(result->idx_first_failure < 0) { INFO("First match failure is %lu", i); result->idx_first_failure = (int)i; } if(abort_on_fail) { result->num_results = i; break; } } } INFO("Aggregate result for %lu / %lu haystack matches: Full passed: %s, first filaure: %d", i, nh, result->all_matched ? "yes" : "no", result->idx_first_failure); TRACE("Output result aggregate size: %lu (alloc: %p)", sizeof(comp_multires_t) + (sizeof(struct comp_single_result) * nh), result); return result; }