Your logic is messed up. You are re-creating the same output dataset each time you call the macro, that is why only the last one still exists.
Your problem doesn't really look like something that needs a macro , but if you did want to use a macro you need to have it only generate the two assignment statements. Then you can call it four times in the middle of a single data step.
%macro gain(g);
&g._ss_gain=&g._ss_501-&g._ss_403;
&g._pl_gain=&g._pl_501-&g._pl_403;
%mend;
data a501_403_v1;
set a501_403;
%gain (listening);
%gain (reading);
%gain (writing);
%gain (speaking);
run;