diff --git a/mm/migrate.c b/mm/migrate.c
index a6a7743ee98f002c7f0ff3d410a2f99392c321cd..a6311e46f6057a665b173e808bf1c03c6990ec7a 100644
--- a/mm/migrate.c
+++ b/mm/migrate.c
@@ -3239,8 +3239,18 @@ static int migration_offline_cpu(unsigned int cpu)
  * set_migration_target_nodes().
  */
 static int __meminit migrate_on_reclaim_callback(struct notifier_block *self,
-						 unsigned long action, void *arg)
+						 unsigned long action, void *_arg)
 {
+	struct memory_notify *arg = _arg;
+
+	/*
+	 * Only update the node migration order when a node is
+	 * changing status, like online->offline.  This avoids
+	 * the overhead of synchronize_rcu() in most cases.
+	 */
+	if (arg->status_change_nid < 0)
+		return notifier_from_errno(0);
+
 	switch (action) {
 	case MEM_GOING_OFFLINE:
 		/*