From 2d41ab6d371df5a54f3ba8ca5279b6d4973b247e Mon Sep 17 00:00:00 2001
From: Yedidya Feldblum <yfeldblum@fb.com>
Date: Fri, 26 Apr 2019 19:14:24 -0700
Subject: [PATCH] Let RequestContext::setContext take by reference

Summary: [Folly] Let `RequestContext::setContext` and `RequestContextScopeGuard` members take `shared_ptr<RequestContex>` by reference. Saves a small amount on code size and runtime performance due to code size.

Reviewed By: spalamarchuk

Differential Revision: D15074704

fbshipit-source-id: 20f1149b8c56d6c4375d63fe21560bdda5e5ccae
---
 folly/io/async/Request.cpp | 9 ++++++++-
 folly/io/async/Request.h   | 8 ++++++--
 2 files changed, 14 insertions(+), 3 deletions(-)

diff --git a/folly/io/async/Request.cpp b/folly/io/async/Request.cpp
index 467bf30e0..d9a914491 100644
--- a/folly/io/async/Request.cpp
+++ b/folly/io/async/Request.cpp
@@ -229,7 +229,14 @@ void exec_set_difference(const TData& data, const TData& other, TExec&& exec) {
 } // namespace
 
 std::shared_ptr<RequestContext> RequestContext::setContext(
-    std::shared_ptr<RequestContext> newCtx) {
+    std::shared_ptr<RequestContext> const& newCtx) {
+  return setContext(copy(newCtx));
+}
+
+std::shared_ptr<RequestContext> RequestContext::setContext(
+    std::shared_ptr<RequestContext>&& newCtx_) {
+  auto newCtx = std::move(newCtx_); // enforce that it is really moved-from
+
   auto& staticCtx = getStaticContext();
   if (newCtx == staticCtx) {
     return newCtx;
diff --git a/folly/io/async/Request.h b/folly/io/async/Request.h
index a71accb4f..e6d83d695 100644
--- a/folly/io/async/Request.h
+++ b/folly/io/async/Request.h
@@ -191,7 +191,9 @@ class RequestContext {
   // A shared_ptr is used, because many request may fan out across
   // multiple threads, or do post-send processing, etc.
   static std::shared_ptr<RequestContext> setContext(
-      std::shared_ptr<RequestContext> ctx);
+      std::shared_ptr<RequestContext> const& ctx);
+  static std::shared_ptr<RequestContext> setContext(
+      std::shared_ptr<RequestContext>&& ctx);
 
   static std::shared_ptr<RequestContext> saveContext() {
     return getStaticContext();
@@ -271,7 +273,9 @@ class RequestContextScopeGuard {
 
   // Set a RequestContext that was previously captured by saveContext(). It will
   // be automatically reset to the original value when this goes out of scope.
-  explicit RequestContextScopeGuard(std::shared_ptr<RequestContext> ctx)
+  explicit RequestContextScopeGuard(std::shared_ptr<RequestContext> const& ctx)
+      : prev_(RequestContext::setContext(ctx)) {}
+  explicit RequestContextScopeGuard(std::shared_ptr<RequestContext>&& ctx)
       : prev_(RequestContext::setContext(std::move(ctx))) {}
 
   ~RequestContextScopeGuard() {
-- 
2.26.2