diff options
Diffstat (limited to 'net/dsa/dsa2.c')
-rw-r--r-- | net/dsa/dsa2.c | 39 |
1 files changed, 29 insertions, 10 deletions
diff --git a/net/dsa/dsa2.c b/net/dsa/dsa2.c index f8445fa73448..b501c90aabe4 100644 --- a/net/dsa/dsa2.c +++ b/net/dsa/dsa2.c | |||
@@ -259,8 +259,11 @@ static int dsa_port_setup(struct dsa_port *dp) | |||
259 | const unsigned char *id = (const unsigned char *)&dst->index; | 259 | const unsigned char *id = (const unsigned char *)&dst->index; |
260 | const unsigned char len = sizeof(dst->index); | 260 | const unsigned char len = sizeof(dst->index); |
261 | struct devlink_port *dlp = &dp->devlink_port; | 261 | struct devlink_port *dlp = &dp->devlink_port; |
262 | bool dsa_port_link_registered = false; | ||
263 | bool devlink_port_registered = false; | ||
262 | struct devlink *dl = ds->devlink; | 264 | struct devlink *dl = ds->devlink; |
263 | int err; | 265 | bool dsa_port_enabled = false; |
266 | int err = 0; | ||
264 | 267 | ||
265 | switch (dp->type) { | 268 | switch (dp->type) { |
266 | case DSA_PORT_TYPE_UNUSED: | 269 | case DSA_PORT_TYPE_UNUSED: |
@@ -272,15 +275,19 @@ static int dsa_port_setup(struct dsa_port *dp) | |||
272 | dp->index, false, 0, id, len); | 275 | dp->index, false, 0, id, len); |
273 | err = devlink_port_register(dl, dlp, dp->index); | 276 | err = devlink_port_register(dl, dlp, dp->index); |
274 | if (err) | 277 | if (err) |
275 | return err; | 278 | break; |
279 | devlink_port_registered = true; | ||
276 | 280 | ||
277 | err = dsa_port_link_register_of(dp); | 281 | err = dsa_port_link_register_of(dp); |
278 | if (err) | 282 | if (err) |
279 | return err; | 283 | break; |
284 | dsa_port_link_registered = true; | ||
280 | 285 | ||
281 | err = dsa_port_enable(dp, NULL); | 286 | err = dsa_port_enable(dp, NULL); |
282 | if (err) | 287 | if (err) |
283 | return err; | 288 | break; |
289 | dsa_port_enabled = true; | ||
290 | |||
284 | break; | 291 | break; |
285 | case DSA_PORT_TYPE_DSA: | 292 | case DSA_PORT_TYPE_DSA: |
286 | memset(dlp, 0, sizeof(*dlp)); | 293 | memset(dlp, 0, sizeof(*dlp)); |
@@ -288,15 +295,19 @@ static int dsa_port_setup(struct dsa_port *dp) | |||
288 | dp->index, false, 0, id, len); | 295 | dp->index, false, 0, id, len); |
289 | err = devlink_port_register(dl, dlp, dp->index); | 296 | err = devlink_port_register(dl, dlp, dp->index); |
290 | if (err) | 297 | if (err) |
291 | return err; | 298 | break; |
299 | devlink_port_registered = true; | ||
292 | 300 | ||
293 | err = dsa_port_link_register_of(dp); | 301 | err = dsa_port_link_register_of(dp); |
294 | if (err) | 302 | if (err) |
295 | return err; | 303 | break; |
304 | dsa_port_link_registered = true; | ||
296 | 305 | ||
297 | err = dsa_port_enable(dp, NULL); | 306 | err = dsa_port_enable(dp, NULL); |
298 | if (err) | 307 | if (err) |
299 | return err; | 308 | break; |
309 | dsa_port_enabled = true; | ||
310 | |||
300 | break; | 311 | break; |
301 | case DSA_PORT_TYPE_USER: | 312 | case DSA_PORT_TYPE_USER: |
302 | memset(dlp, 0, sizeof(*dlp)); | 313 | memset(dlp, 0, sizeof(*dlp)); |
@@ -304,18 +315,26 @@ static int dsa_port_setup(struct dsa_port *dp) | |||
304 | dp->index, false, 0, id, len); | 315 | dp->index, false, 0, id, len); |
305 | err = devlink_port_register(dl, dlp, dp->index); | 316 | err = devlink_port_register(dl, dlp, dp->index); |
306 | if (err) | 317 | if (err) |
307 | return err; | 318 | break; |
319 | devlink_port_registered = true; | ||
308 | 320 | ||
309 | dp->mac = of_get_mac_address(dp->dn); | 321 | dp->mac = of_get_mac_address(dp->dn); |
310 | err = dsa_slave_create(dp); | 322 | err = dsa_slave_create(dp); |
311 | if (err) | 323 | if (err) |
312 | return err; | 324 | break; |
313 | 325 | ||
314 | devlink_port_type_eth_set(dlp, dp->slave); | 326 | devlink_port_type_eth_set(dlp, dp->slave); |
315 | break; | 327 | break; |
316 | } | 328 | } |
317 | 329 | ||
318 | return 0; | 330 | if (err && dsa_port_enabled) |
331 | dsa_port_disable(dp); | ||
332 | if (err && dsa_port_link_registered) | ||
333 | dsa_port_link_unregister_of(dp); | ||
334 | if (err && devlink_port_registered) | ||
335 | devlink_port_unregister(dlp); | ||
336 | |||
337 | return err; | ||
319 | } | 338 | } |
320 | 339 | ||
321 | static void dsa_port_teardown(struct dsa_port *dp) | 340 | static void dsa_port_teardown(struct dsa_port *dp) |