| 273 | } |
| 274 | |
| 275 | static void |
| 276 | fs_dev_remove(struct sub_device *sdev) |
| 277 | { |
| 278 | int ret; |
| 279 | |
| 280 | if (sdev == NULL) |
| 281 | return; |
| 282 | switch (sdev->state) { |
| 283 | case DEV_STARTED: |
| 284 | failsafe_rx_intr_uninstall_subdevice(sdev); |
| 285 | ret = rte_eth_dev_stop(PORT_ID(sdev)); |
| 286 | if (ret < 0) |
| 287 | ERROR("Failed to stop sub-device %u", SUB_ID(sdev)); |
| 288 | sdev->state = DEV_ACTIVE; |
| 289 | /* fallthrough */ |
| 290 | case DEV_ACTIVE: |
| 291 | failsafe_eth_dev_unregister_callbacks(sdev); |
| 292 | ret = rte_eth_dev_close(PORT_ID(sdev)); |
| 293 | if (ret < 0) { |
| 294 | ERROR("Port close failed for sub-device %u", |
| 295 | PORT_ID(sdev)); |
| 296 | } |
| 297 | sdev->state = DEV_PROBED; |
| 298 | /* fallthrough */ |
| 299 | case DEV_PROBED: |
| 300 | ret = rte_dev_remove(sdev->dev); |
| 301 | if (ret < 0) { |
| 302 | ERROR("Bus detach failed for sub_device %u", |
| 303 | SUB_ID(sdev)); |
| 304 | } else { |
| 305 | rte_eth_dev_release_port(ETH(sdev)); |
| 306 | } |
| 307 | sdev->state = DEV_PARSED; |
| 308 | /* fallthrough */ |
| 309 | case DEV_PARSED: |
| 310 | case DEV_UNDEFINED: |
| 311 | sdev->state = DEV_UNDEFINED; |
| 312 | sdev->sdev_port_id = RTE_MAX_ETHPORTS; |
| 313 | /* the end */ |
| 314 | break; |
| 315 | } |
| 316 | sdev->remove = 0; |
| 317 | failsafe_hotplug_alarm_install(fs_dev(sdev)); |
| 318 | } |
| 319 | |
| 320 | static void |
| 321 | fs_dev_stats_save(struct sub_device *sdev) |
no test coverage detected