rcu_read_unlock();
 }
 
+static int fib6_config_validate(struct fib6_config *cfg,
+                               struct netlink_ext_ack *extack)
+{
+       /* RTF_PCPU is an internal flag; can not be set by userspace */
+       if (cfg->fc_flags & RTF_PCPU) {
+               NL_SET_ERR_MSG(extack, "Userspace can not set RTF_PCPU");
+               goto errout;
+       }
+
+       /* RTF_CACHE is an internal flag; can not be set by userspace */
+       if (cfg->fc_flags & RTF_CACHE) {
+               NL_SET_ERR_MSG(extack, "Userspace can not set RTF_CACHE");
+               goto errout;
+       }
+
+       if (cfg->fc_type > RTN_MAX) {
+               NL_SET_ERR_MSG(extack, "Invalid route type");
+               goto errout;
+       }
+
+       if (cfg->fc_dst_len > 128) {
+               NL_SET_ERR_MSG(extack, "Invalid prefix length");
+               goto errout;
+       }
+
+#ifdef CONFIG_IPV6_SUBTREES
+       if (cfg->fc_src_len > 128) {
+               NL_SET_ERR_MSG(extack, "Invalid source address length");
+               goto errout;
+       }
+
+       if (cfg->fc_nh_id && cfg->fc_src_len) {
+               NL_SET_ERR_MSG(extack, "Nexthops can not be used with source routing");
+               goto errout;
+       }
+#else
+       if (cfg->fc_src_len) {
+               NL_SET_ERR_MSG(extack,
+                              "Specifying source address requires IPV6_SUBTREES to be enabled");
+               goto errout;
+       }
+#endif
+       return 0;
+errout:
+       return -EINVAL;
+}
+
 static void rtmsg_to_fib6_config(struct net *net,
                                 struct in6_rtmsg *rtmsg,
                                 struct fib6_config *cfg)
 
        switch (cmd) {
        case SIOCADDRT:
+               err = fib6_config_validate(&cfg, NULL);
+               if (err)
+                       break;
+
                /* Only do the default setting of fc_metric in route adding */
                if (cfg.fc_metric == 0)
                        cfg.fc_metric = IP6_RT_PRIO_USER;
                }
        }
 
-       if (newroute) {
-               /* RTF_PCPU is an internal flag; can not be set by userspace */
-               if (cfg->fc_flags & RTF_PCPU) {
-                       NL_SET_ERR_MSG(extack, "Userspace can not set RTF_PCPU");
-                       goto errout;
-               }
-
-               /* RTF_CACHE is an internal flag; can not be set by userspace */
-               if (cfg->fc_flags & RTF_CACHE) {
-                       NL_SET_ERR_MSG(extack, "Userspace can not set RTF_CACHE");
-                       goto errout;
-               }
-
-               if (cfg->fc_type > RTN_MAX) {
-                       NL_SET_ERR_MSG(extack, "Invalid route type");
-                       goto errout;
-               }
-
-               if (cfg->fc_dst_len > 128) {
-                       NL_SET_ERR_MSG(extack, "Invalid prefix length");
-                       goto errout;
-               }
-
-#ifdef CONFIG_IPV6_SUBTREES
-               if (cfg->fc_src_len > 128) {
-                       NL_SET_ERR_MSG(extack, "Invalid source address length");
-                       goto errout;
-               }
-
-               if (cfg->fc_nh_id &&  cfg->fc_src_len) {
-                       NL_SET_ERR_MSG(extack, "Nexthops can not be used with source routing");
-                       goto errout;
-               }
-#else
-               if (cfg->fc_src_len) {
-                       NL_SET_ERR_MSG(extack,
-                                      "Specifying source address requires IPV6_SUBTREES to be enabled");
-                       goto errout;
-               }
-#endif
-       }
-
        err = 0;
 errout:
        return err;
        if (err < 0)
                return err;
 
+       err = fib6_config_validate(&cfg, extack);
+       if (err)
+               return err;
+
        if (cfg.fc_metric == 0)
                cfg.fc_metric = IP6_RT_PRIO_USER;