summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorDavid Lönnhager <david.l@mullvad.net>2020-09-18 13:27:55 +0200
committerDavid Lönnhager <david.l@mullvad.net>2020-09-22 13:12:18 +0200
commit76ad0fdf0b9ba3141d9c1029158352e073047dc5 (patch)
tree199b0f93ffe8ce116902f13045fc6666a0c82ce5
parentbb1e50525c97f7e597860a6ecfc6d2af82f35dc4 (diff)
downloadmullvadvpn-76ad0fdf0b9ba3141d9c1029158352e073047dc5.tar.xz
mullvadvpn-76ad0fdf0b9ba3141d9c1029158352e073047dc5.zip
Add function for obtaining a free routing table
-rw-r--r--talpid-core/src/routing/linux.rs35
1 files changed, 35 insertions, 0 deletions
diff --git a/talpid-core/src/routing/linux.rs b/talpid-core/src/routing/linux.rs
index a314c4f112..404bda606f 100644
--- a/talpid-core/src/routing/linux.rs
+++ b/talpid-core/src/routing/linux.rs
@@ -155,6 +155,41 @@ impl RouteManagerImpl {
Ok(monitor)
}
+ async fn find_free_table_id(&self) -> Result<u32> {
+ let mut request = self.handle.route().get(IpVersion::V4).execute();
+ let mut used_ids = HashSet::new();
+
+ while let Some(route) = request.try_next().await.map_err(Error::NetlinkError)? {
+ let mut id_found = false;
+ for nla in route.nlas {
+ match nla {
+ RouteNla::Table(id) => {
+ used_ids.insert(id);
+ id_found = true;
+ break;
+ }
+ _ => (),
+ }
+ }
+
+ if !id_found {
+ // Use old header ID
+ used_ids.insert(u32::from(route.header.table));
+ }
+ }
+
+ for id in 1..u32::MAX {
+ if id == RT_TABLE_COMPAT as u32 {
+ continue;
+ }
+ if !used_ids.contains(&id) {
+ return Ok(id);
+ }
+ }
+
+ Err(Error::NoFreeRoutingTableId)
+ }
+
/// Set up policy-based routing table for marked packets.
/// Returns the routing table id.
async fn initialize_exclusions_table() -> Result<i32> {