Implementing a stack using a linked-list
Redundant Code

In your push() function, you have these two cases which are redundant:


// if stack is empty
if (head == NULL)
{
    strcpy(temp -&gt; string, element);
    temp -&gt; next = NULL;
    return temp;
}

strcpy(temp -&gt; string, element);
temp -&gt; next = head;
return temp;



You can just remove the special case for head == NULL and be left with this, which handles both cases:

strcpy(temp -&gt; string, element);
temp -&gt; next = head;
return temp;


Better to iterate than recurse

Your destroy_stack() function is recursive, and that could be a problem if the stack has millions of elements because it could cause your program stack to overflow.  It is easy enough to write an iterative version of that function instead, like this:

void destroy_stack(node *p)
{
    while (p != NULL)
    {
        node *next = p-&gt;next;
        free(p);
        p = next;
    }
}


Minor issues


In push(), using strcpy() is unsafe because element might exceed 20 characters and you will overflow your buffer.
In push(), if malloc() returns NULL, you return NULL and thus destroy/leak the rest of the stack.  Perhaps you should just return head instead, to preserve the rest of the stack.
In pop(), you might want to check for head == NULL, otherwise you must depend on the caller to never pass NULL to your function.