Always check the return value from system calls like rename; you'd see that it failed. The readdir returns names of files in $dir but they're not prefixed with it so your rename("$name.$old","$name.$new") is trying to rename files in the directory you ran from not the one you named in $dir (you'd need to use "$dir/$name.$old" instead).
You might also check out something like Path::Tiny for another interface which might be easier to work with.
Edit: And just for clarity, by checking the return value I mean when you call things like opendir or rename that interact with the OS you should check their return value and print a meaningful error message when things go wrong. E.g.:
opendir( my $dirhandle, $dir ) or die "Can't opendir directory '$dir':
+ $!\n";
rename( "$dir/$name.$old", "$dir/$name.$new" )
or warn "Problem renaming '$dir/$name.$old' to '$dir/$name.$new': $!
+\n";
The cake is a lie.
The cake is a lie.
The cake is a lie.