)]}'
{
  "commit": "463d46044f04013306a4893242f65788b8a16b2e",
  "tree": "92cff23b046fa849577916868a6f3c806bfc8710",
  "parents": [
    "1bba3900ca18bdae28d1b9fa10f16a8f8cb2ada1"
  ],
  "author": {
    "name": "Tze-nan Wu",
    "email": "Tze-nan.Wu@mediatek.com",
    "time": "Thu Jul 17 13:53:38 2025 +0800"
  },
  "committer": {
    "name": "Neeraj Upadhyay (AMD)",
    "email": "neeraj.upadhyay@kernel.org",
    "time": "Fri Jul 18 09:25:34 2025 +0530"
  },
  "message": "rcu: Fix delayed execution of hurry callbacks\n\nWe observed a regression in our customer’s environment after enabling\nCONFIG_LAZY_RCU. In the Android Update Engine scenario, where ioctl() is\nused heavily, we found that callbacks queued via call_rcu_hurry (such as\npercpu_ref_switch_to_atomic_rcu) can sometimes be delayed by up to 5\nseconds before execution. This occurs because the new grace period does\nnot start immediately after the previous one completes.\n\nThe root cause is that the wake_nocb_gp_defer() function now checks\n\"rdp-\u003enocb_defer_wakeup\" instead of \"rdp_gp-\u003enocb_defer_wakeup\". On CPUs\nthat are not rcuog, \"rdp-\u003enocb_defer_wakeup\" may always be\nRCU_NOCB_WAKE_NOT. This can cause \"rdp_gp-\u003enocb_defer_wakeup\" to be\ndowngraded and the \"rdp_gp-\u003enocb_timer\" to be postponed by up to 10\nseconds, delaying the execution of hurry RCU callbacks.\n\nThe trace log of one scenario we encountered is as follow:\n  // previous GP ends at this point\n  rcu_preempt   [000] d..1.   137.240210: rcu_grace_period: rcu_preempt 8369 end\n  rcu_preempt   [000] .....   137.240212: rcu_grace_period: rcu_preempt 8372 reqwait\n  // call_rcu_hurry enqueues \"percpu_ref_switch_to_atomic_rcu\", the callback waited on by UpdateEngine\n  update_engine [002] d..1.   137.301593: __call_rcu_common: wyy: unlikely p_ref \u003d 00000000********. lazy \u003d 0\n  // FirstQ on cpu 2 rdp_gp-\u003enocb_timer is set to fire after 1 jiffy (4ms)\n  // and the rdp_gp-\u003enocb_defer_wakeup is set to RCU_NOCB_WAKE\n  update_engine [002] d..2.   137.301595: rcu_nocb_wake: rcu_preempt 2 FirstQ on cpu2 with rdp_gp (cpu0).\n  // FirstBQ event on cpu2 during the 1 jiffy, make the timer postpond 10 seconds later.\n  // also, the rdp_gp-\u003enocb_defer_wakeup is overwrite to RCU_NOCB_WAKE_LAZY\n  update_engine [002] d..1.   137.301601: rcu_nocb_wake: rcu_preempt 2 WakeEmptyIsDeferred\n  ...\n  ...\n  ...\n  // before the 10 seconds timeout, cpu0 received another call_rcu_hurry\n  // reset the timer to jiffies+1 and set the waketype \u003d RCU_NOCB_WAKE.\n  kworker/u32:0 [000] d..2.   142.557564: rcu_nocb_wake: rcu_preempt 0 FirstQ\n  kworker/u32:0 [000] d..1.   142.557576: rcu_nocb_wake: rcu_preempt 0 WakeEmptyIsDeferred\n  kworker/u32:0 [000] d..1.   142.558296: rcu_nocb_wake: rcu_preempt 0 WakeNot\n  kworker/u32:0 [000] d..1.   142.558562: rcu_nocb_wake: rcu_preempt 0 WakeNot\n  // idle(do_nocb_deferred_wakeup) wake rcuog due to waketype \u003d\u003d RCU_NOCB_WAKE\n  \u003cidle\u003e        [000] d..1.   142.558786: rcu_nocb_wake: rcu_preempt 0 DoWake\n  \u003cidle\u003e        [000] dN.1.   142.558839: rcu_nocb_wake: rcu_preempt 0 DeferredWake\n  rcuog/0       [000] .....   142.558871: rcu_nocb_wake: rcu_preempt 0 EndSleep\n  rcuog/0       [000] .....   142.558877: rcu_nocb_wake: rcu_preempt 0 Check\n  // finally rcuog request a new GP at this point (5 seconds after the FirstQ event)\n  rcuog/0       [000] d..2.   142.558886: rcu_grace_period: rcu_preempt 8372 newreq\n  rcu_preempt   [001] d..1.   142.559458: rcu_grace_period: rcu_preempt 8373 start\n  ...\n  rcu_preempt   [000] d..1.   142.564258: rcu_grace_period: rcu_preempt 8373 end\n  rcuop/2       [000] D..1.   142.566337: rcu_batch_start: rcu_preempt CBs\u003d219 bl\u003d10\n  // the hurry CB is invoked at this point\n  rcuop/2       [000] b....   142.566352: blk_queue_usage_counter_release: wyy: wakeup. p_ref \u003d 00000000********.\n\nThis patch changes the condition to check \"rdp_gp-\u003enocb_defer_wakeup\" in\nthe lazy path. This prevents an already scheduled \"rdp_gp-\u003enocb_timer\"\nfrom being postponed and avoids overwriting \"rdp_gp-\u003enocb_defer_wakeup\"\nwhen it is not RCU_NOCB_WAKE_NOT.\n\nFixes: 3cb278e73be5 (\"rcu: Make call_rcu() lazy to save power\")\nCo-developed-by: Cheng-jui Wang \u003ccheng-jui.wang@mediatek.com\u003e\nSigned-off-by: Cheng-jui Wang \u003ccheng-jui.wang@mediatek.com\u003e\nCo-developed-by: Lorry.Luo@mediatek.com\nSigned-off-by: Lorry.Luo@mediatek.com\nTested-by: weiyangyang@vivo.com\nSigned-off-by: weiyangyang@vivo.com\nSigned-off-by: Tze-nan Wu \u003cTze-nan.Wu@mediatek.com\u003e\nReviewed-by: Frederic Weisbecker \u003cfrederic@kernel.org\u003e\nSigned-off-by: Neeraj Upadhyay (AMD) \u003cneeraj.upadhyay@kernel.org\u003e\n",
  "tree_diff": [
    {
      "type": "modify",
      "old_id": "08eb9b0e2fab444220ed1491e547d43eeba4941a",
      "old_mode": 33188,
      "old_path": "kernel/rcu/tree_nocb.h",
      "new_id": "e6cd56603cad4d91af9748f43da708acf4e94a28",
      "new_mode": 33188,
      "new_path": "kernel/rcu/tree_nocb.h"
    }
  ]
}
