First case:
char* c = "abcd";
c is of type char *. The base address of the string "abcd" is stored into that. Correct.
Second Case:
char* cArr[3];
cArr is an array of three char *s.
cArr[0] = "A string of of characters.";
cArr[1] = "Another inane comment.";
is also fine and legal. You're storing the base address of the string literals into a variable of type char * (here, cArr[n]). There is no issue with that.
Or are these strings being placed on the heap?
Not really. Standards only specify that the string literals should have static storage duration. Usually string literals are placed in read-only memory locations so you may not be able to modify the strings pointed by cArr[n]. So, basically it's implementation dependent where the string literals are stored. As mentioned in this previous answer, strings are stored in the .rodata section of your binary.