Modifying existing route entry in linux
(Combining various comments into an answer)
Currently, it is not possible to modify a route's metric. As a 2005 message on LKML states:
[...] The metric/priority cannot be changed because we do not have separate fields for the fields to match and the new values so if you specify a metric the entry simply won't be found and the request fails with ENOENT because NLM_F_CREATE is not specified. This is a limitation of the current protocol and it might be a good idea to to change this, however it's non trivial [...]
This seems to apply both to ip route change
and ip route replace
- the former results in an error for me, while the latter creates an additional route as advertised (its man page states that replace
will replace or create a route). This is consistent with the kernel responding with ENOENT, and ip route replace
following up with a route creation request.
So, the solution is to delete the existing route and add a new one. e.g.
ip route del 40.2.2.0/24 via 30.1.2.2
ip route add 40.2.2.0/24 via 30.1.2.2 metric 1234
As noted in a comment to the question, quoting a message on the linux-net mailing list: "The metric/priority cannot be changed [...] This is a limitation of the current protocol [...]."
The only way is to delete the route and add a new one.
This is done using the route
command, example:
sudo route add -net default gw 10.10.0.1 netmask 0.0.0.0 dev wlan0 metric 1
Debian manpage for the route command
ifmetric
will allow you to change your route metric on the fly, given the interface the routes you want to change are going through.
Usage
ifmetric <iface> [<metric>]
For example, use ifmetric tun0 12
to change the metric to 12 for all routes going through tun0
.