Полагаю, вы имеете в виду p1 = p2 (то есть значение p2 копируется в p1).
Указатели содержат адреса в (виртуальной) памяти.
Таким образом, p1 теперь содержит значение p2, которое является адресом второго значения.
В
*p1 = 20;
Значение по адресу памяти p1 (то же самое, что и p2) теперь принимает значение 20.
firstvalue остается неизменным и на него больше не ссылается ни один из двух указателей p1 и p2