Andiamo con ordine
Innanzitutto, ci sono un po' di erroretti. Il primo e più visibile è:
Codice: Seleziona tutto
assert (!regexec (&preg, str, MAX_MATCH, matches, REG_EXTENDED));
regexec usa flags completamente diversi da regcomp, e REG_EXTENDED è un flag di regcomp.
il secondo è:
Codice: Seleziona tutto
strncpy (buff, str + matches[i].rm_so, matches[i].rm_eo - matches[i].rm_so);
strncpy copia pezzi di stringa SENZA aggiungere il terminatore, ovviamente. Significa che ti troverai con pezzi delle stringhe più grandi mischiati a quelli delle stringhe più piccole.. non è bello =)
Al di la di questo, il punto è:
regexec non trova tutte le occorrenze presenti in una stringa, ma solo la prima. Devi fare un ciclo se vuoi trovarle tutte, aumentando l'offset del puntatore alla stringa ogni volta ed usando ad hoc il flag REG_NOTBOL.
L'array matches è un array poichè restituisce non tutte le occorrenze di un pattern in una stringa (che per inciso è terminata da NULL, non da NEWLINE), ma le occorrenze dei subpattern, se presenti. I subpattern sono le parti della regular expression fra parentesi.
Per fartelo capire, modificherò un pelo il tuo esempio (un pelo nel senso che non lo stravolgo, anche se io l'avrei programmato diversamente):
Codice: Seleziona tutto
#include <stdio.h>
#include <string.h>
#include <regex.h>
#include <assert.h>
#define MAX_MATCH 10
int main (void)
{
char str[] = "AAAAAAciao1ZZZZZZAAAAAAciao5ZZZZZZ"
, buff[50];
regex_t preg;
regmatch_t matches[MAX_MATCH];
u_short i;
assert (!regcomp (&preg, "ci(ao)", REG_EXTENDED));
assert (!regexec (&preg, str, MAX_MATCH, matches, 0));
for (i = 0; matches[i].rm_so >= 0 && i < MAX_MATCH; i++)
{
memset(buff, 0, sizeof(buff));
strncpy (buff, str + matches[i].rm_so, matches[i].rm_eo - matches[i].rm_so);
printf ("Match %u: %s\n", i, buff);
}
regfree (&preg);
return 0;
}
Output:
Codice: Seleziona tutto
samuele@nuitari-laptop:~$ gcc prova.c && ./a.out
Match 0: ciao
Match 1: ao
Se vuoi un esempio di codice con il ciclo per trovare tutte le occorrenze, dillo =)