WIP: Start auditing all `forward_request` calls on the server

Antonio Scandurra created

When the host returns an error after a server has forwarded a request,
we want to surface that error to the guest. At the moment, the server
just returns early leaving some requests unresponded on the guest.

I started auditing all the code paths where we do that, but I am
wondering whether there's some other approach that would prevent us
from repeating this mistake in other code paths.

Change summary

crates/server/src/rpc.rs | 70 +++++++++++++++++++++++++++++++++---------
1 file changed, 55 insertions(+), 15 deletions(-)

Detailed changes

crates/server/src/rpc.rs 🔗

@@ -684,11 +684,19 @@ impl Server {
 
         let sender = request.sender_id;
         let receipt = request.receipt();
-        let response = self
+        match self
             .peer
             .forward_request(sender, host, request.payload.clone())
-            .await?;
-        self.peer.respond(receipt, response)?;
+            .await
+        {
+            Ok(response) => self.peer.respond(receipt, response)?,
+            Err(error) => self.peer.respond_with_error(
+                receipt,
+                proto::Error {
+                    message: error.to_string(),
+                },
+            )?,
+        }
 
         Ok(())
     }
@@ -708,11 +716,19 @@ impl Server {
 
         let sender = request.sender_id;
         let receipt = request.receipt();
-        let response = self
+        match self
             .peer
             .forward_request(sender, host, request.payload.clone())
-            .await?;
-        self.peer.respond(receipt, response)?;
+            .await
+        {
+            Ok(response) => self.peer.respond(receipt, response)?,
+            Err(error) => self.peer.respond_with_error(
+                receipt,
+                proto::Error {
+                    message: error.to_string(),
+                },
+            )?,
+        }
         Ok(())
     }
 
@@ -731,11 +747,19 @@ impl Server {
 
         let sender = request.sender_id;
         let receipt = request.receipt();
-        let response = self
+        match self
             .peer
             .forward_request(sender, host, request.payload.clone())
-            .await?;
-        self.peer.respond(receipt, response)?;
+            .await
+        {
+            Ok(response) => self.peer.respond(receipt, response)?,
+            Err(error) => self.peer.respond_with_error(
+                receipt,
+                proto::Error {
+                    message: error.to_string(),
+                },
+            )?,
+        }
         Ok(())
     }
 
@@ -754,11 +778,19 @@ impl Server {
 
         let sender = request.sender_id;
         let receipt = request.receipt();
-        let response = self
+        match self
             .peer
             .forward_request(sender, host, request.payload.clone())
-            .await?;
-        self.peer.respond(receipt, response)?;
+            .await
+        {
+            Ok(response) => self.peer.respond(receipt, response)?,
+            Err(error) => self.peer.respond_with_error(
+                receipt,
+                proto::Error {
+                    message: error.to_string(),
+                },
+            )?,
+        }
         Ok(())
     }
 
@@ -777,11 +809,19 @@ impl Server {
 
         let sender = request.sender_id;
         let receipt = request.receipt();
-        let response = self
+        match self
             .peer
             .forward_request(sender, host, request.payload.clone())
-            .await?;
-        self.peer.respond(receipt, response)?;
+            .await
+        {
+            Ok(response) => self.peer.respond(receipt, response)?,
+            Err(error) => self.peer.respond_with_error(
+                receipt,
+                proto::Error {
+                    message: error.to_string(),
+                },
+            )?,
+        }
         Ok(())
     }