Żeby cokolwiek zapisać w pamięci, musisz mieć tę pamięć najpierw zarezerwowaną dla swojego użytku. W poniższym kodzie łamiesz tę zasadę:
char *napis;
gets(napis);
Zapis char *napis tworzy jedynie wskaźnik na znak - żeby coś przypisać pod adres wskazywany przez napis, musisz dokonać alokacji pamięci.
Wybierając funkcję gets() do wczytania łańcucha, praktycznie pozbawiasz się kontroli nad długością pobranego łańcucha. Już chyba lepszym rozwiązaniem byłoby utworzenie na początek jakiejś małej tablicy i wczytywanie łańcucha znak po znaku, a w razie przepełnienia bufora - realokacja tablicy na większą.