innanzitutto buon anno!!!
per quanto riguarda il tuo problema direi che in copy_array() hai sbagliato a fare la malloc. se tu dichiari char **a; quello è un puntatore di puntatore che serve per realizzare un array di stringhe. facendo come hai scritto tu
a1= (char **) malloc (sizeof(char)*20);
è sbagliato perchè allochi spazio per 20 caratteri e non 20 puntatori a caratteri e poi casti a puntatore di puntatore. direi che si dovrebbe correggere in questo modo:
a1= (char **) malloc (sizeof(char *)*20);
in questo modo allochi spazio per 20 stringhe, ora però devi allocare spazio per ogni stringa, così
for (i=0; i<20; ++i) a1[i]= (char *) malloc (sizeof(char)*15);
in questo modo a1 è un array di stringhe composte da 15 caratteri.
per quanto riguarda la copy_struct() ora non ti posso aiutare sono ancora troppo intontito...