Questo modo di allocare l'array è sbaglaito
int i,j;
int M[i][j];
All'inizio del programma, prima di chiedere in input i e j, non sai quanto valgono e l'array non ha dimensioni certe.
Inoltre non capisco perché tutto quel giro con i puntatori p e q ... non puoi semplicemente utilizzare i e j ?