mirror of
https://gitlab.freedesktop.org/NetworkManager/NetworkManager
synced 2024-07-21 10:14:41 +00:00
merge: branch 'bg/sriov-reset-on-failure'
https://bugzilla.redhat.com/show_bug.cgi?id=1819587 https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/457
This commit is contained in:
commit
6ca98f5b04
|
@ -614,6 +614,7 @@ typedef struct _NMDevicePrivate {
|
|||
SriovOp *pending; /* SR-IOV operation currently running */
|
||||
SriovOp *next; /* next SR-IOV operation scheduled */
|
||||
} sriov;
|
||||
guint sriov_reset_pending;
|
||||
|
||||
struct {
|
||||
guint timeout_id;
|
||||
|
@ -4765,15 +4766,12 @@ sriov_op_cb (GError *error, gpointer user_data)
|
|||
|
||||
nm_assert (op == priv->sriov.pending);
|
||||
|
||||
priv->sriov.pending = NULL;
|
||||
|
||||
g_clear_object (&op->cancellable);
|
||||
|
||||
if (op->callback)
|
||||
op->callback (error, op->callback_data);
|
||||
|
||||
nm_assert (!priv->sriov.pending);
|
||||
|
||||
priv->sriov.pending = NULL;
|
||||
nm_g_slice_free (op);
|
||||
|
||||
if (priv->sriov.next) {
|
||||
|
@ -4791,6 +4789,8 @@ sriov_op_queue_op (NMDevice *self,
|
|||
if (priv->sriov.next) {
|
||||
SriovOp *op_next = g_steal_pointer (&priv->sriov.next);
|
||||
|
||||
priv->sriov.next = op;
|
||||
|
||||
/* Cancel the next operation immediately */
|
||||
if (op_next->callback) {
|
||||
gs_free_error GError *error = NULL;
|
||||
|
@ -4800,17 +4800,10 @@ sriov_op_queue_op (NMDevice *self,
|
|||
}
|
||||
|
||||
nm_g_slice_free (op_next);
|
||||
return;
|
||||
}
|
||||
|
||||
if (!priv->sriov.pending) {
|
||||
/* This (having "next" set but "pending" not) can only happen if we are
|
||||
* called from inside the callback again.
|
||||
*
|
||||
* That means we append the new request as "next" and return. Once
|
||||
* the callback returns, it will schedule the request. */
|
||||
priv->sriov.next = op;
|
||||
return;
|
||||
}
|
||||
} else if (priv->sriov.pending) {
|
||||
if (priv->sriov.pending) {
|
||||
priv->sriov.next = op;
|
||||
g_cancellable_cancel (priv->sriov.pending->cancellable);
|
||||
return;
|
||||
|
@ -15927,26 +15920,50 @@ deactivate_ready (NMDevice *self, NMDeviceStateReason reason)
|
|||
if (priv->dispatcher.call_id)
|
||||
return;
|
||||
|
||||
if ( priv->sriov.pending
|
||||
|| priv->sriov.next)
|
||||
if (priv->sriov_reset_pending > 0)
|
||||
return;
|
||||
|
||||
nm_device_queue_state (self, NM_DEVICE_STATE_DISCONNECTED, reason);
|
||||
if (priv->state == NM_DEVICE_STATE_DEACTIVATING)
|
||||
nm_device_queue_state (self, NM_DEVICE_STATE_DISCONNECTED, reason);
|
||||
}
|
||||
|
||||
static void
|
||||
sriov_deactivate_cb (GError *error, gpointer user_data)
|
||||
sriov_reset_on_deactivate_cb (GError *error, gpointer user_data)
|
||||
{
|
||||
NMDevice *self;
|
||||
NMDevicePrivate *priv;
|
||||
gpointer reason;
|
||||
|
||||
if (nm_utils_error_is_cancelled_or_disposing (error))
|
||||
nm_utils_user_data_unpack (user_data, &self, &reason);
|
||||
priv = NM_DEVICE_GET_PRIVATE (self);
|
||||
nm_assert (priv->sriov_reset_pending > 0);
|
||||
priv->sriov_reset_pending--;
|
||||
|
||||
if (nm_utils_error_is_cancelled (error))
|
||||
return;
|
||||
|
||||
nm_utils_user_data_unpack (user_data, &self, &reason);
|
||||
deactivate_ready (self, (NMDeviceStateReason) reason);
|
||||
}
|
||||
|
||||
static void
|
||||
sriov_reset_on_failure_cb (GError *error, gpointer user_data)
|
||||
{
|
||||
NMDevice *self = user_data;
|
||||
NMDevicePrivate *priv = NM_DEVICE_GET_PRIVATE (self);
|
||||
|
||||
nm_assert (priv->sriov_reset_pending > 0);
|
||||
priv->sriov_reset_pending--;
|
||||
|
||||
if (nm_utils_error_is_cancelled (error))
|
||||
return;
|
||||
|
||||
if (priv->state == NM_DEVICE_STATE_FAILED) {
|
||||
nm_device_queue_state (self,
|
||||
NM_DEVICE_STATE_DISCONNECTED,
|
||||
NM_DEVICE_STATE_REASON_NONE);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
deactivate_async_ready (NMDevice *self,
|
||||
GError *error,
|
||||
|
@ -16273,10 +16290,11 @@ _set_state_full (NMDevice *self,
|
|||
|
||||
if ( priv->ifindex > 0
|
||||
&& (s_sriov = nm_device_get_applied_setting (self, NM_TYPE_SETTING_SRIOV))) {
|
||||
priv->sriov_reset_pending++;
|
||||
sriov_op_queue (self,
|
||||
0,
|
||||
NM_TERNARY_TRUE,
|
||||
sriov_deactivate_cb,
|
||||
sriov_reset_on_deactivate_cb,
|
||||
nm_utils_user_data_pack (self, (gpointer) reason));
|
||||
}
|
||||
}
|
||||
|
@ -16328,6 +16346,16 @@ _set_state_full (NMDevice *self,
|
|||
if (sett_conn && !nm_settings_connection_get_timestamp (sett_conn, NULL))
|
||||
nm_settings_connection_update_timestamp (sett_conn, (guint64) 0);
|
||||
|
||||
if ( priv->ifindex > 0
|
||||
&& (s_sriov = nm_device_get_applied_setting (self, NM_TYPE_SETTING_SRIOV))) {
|
||||
priv->sriov_reset_pending++;
|
||||
sriov_op_queue (self,
|
||||
0,
|
||||
NM_TERNARY_TRUE,
|
||||
sriov_reset_on_failure_cb,
|
||||
self);
|
||||
break;
|
||||
}
|
||||
/* Schedule the transition to DISCONNECTED. The device can't transition
|
||||
* immediately because we can't change states again from the state
|
||||
* handler for a variety of reasons.
|
||||
|
@ -17892,6 +17920,12 @@ dispose (GObject *object)
|
|||
nm_clear_g_source (&priv->concheck_x[0].p_cur_id);
|
||||
nm_clear_g_source (&priv->concheck_x[1].p_cur_id);
|
||||
|
||||
nm_assert (!priv->sriov.pending);
|
||||
if (priv->sriov.next) {
|
||||
nm_g_slice_free (priv->sriov.next);
|
||||
priv->sriov.next = NULL;
|
||||
}
|
||||
|
||||
G_OBJECT_CLASS (nm_device_parent_class)->dispose (object);
|
||||
|
||||
if (nm_clear_g_source (&priv->queued_state.id)) {
|
||||
|
|
|
@ -7254,7 +7254,7 @@ link_supports_sriov (NMPlatform *platform, int ifindex)
|
|||
nm_auto_pop_netns NMPNetns *netns = NULL;
|
||||
nm_auto_close int dirfd = -1;
|
||||
char ifname[IFNAMSIZ];
|
||||
int total = -1;
|
||||
int num = -1;
|
||||
|
||||
if (!nm_platform_netns_push (platform, &netns))
|
||||
return FALSE;
|
||||
|
@ -7263,13 +7263,13 @@ link_supports_sriov (NMPlatform *platform, int ifindex)
|
|||
if (dirfd < 0)
|
||||
return FALSE;
|
||||
|
||||
total = nm_platform_sysctl_get_int32 (platform,
|
||||
NMP_SYSCTL_PATHID_NETDIR (dirfd,
|
||||
ifname,
|
||||
"device/sriov_totalvfs"),
|
||||
-1);
|
||||
num = nm_platform_sysctl_get_int32 (platform,
|
||||
NMP_SYSCTL_PATHID_NETDIR (dirfd,
|
||||
ifname,
|
||||
"device/sriov_numvfs"),
|
||||
-1);
|
||||
|
||||
return total > 0;
|
||||
return num != -1;
|
||||
}
|
||||
|
||||
static int
|
||||
|
@ -7412,15 +7412,7 @@ link_set_sriov_params_async (NMPlatform *platform,
|
|||
ifname,
|
||||
"device/sriov_totalvfs"),
|
||||
10, 0, G_MAXUINT, 0);
|
||||
if (errno) {
|
||||
g_set_error (&error,
|
||||
NM_UTILS_ERROR,
|
||||
NM_UTILS_ERROR_UNKNOWN,
|
||||
"failed reading sriov_totalvfs value: %s",
|
||||
nm_strerror_native (errno));
|
||||
goto out_idle;
|
||||
}
|
||||
if (num_vfs > total) {
|
||||
if (!errno && num_vfs > total) {
|
||||
_LOGW ("link: %d only supports %u VFs (requested %u)", ifindex, total, num_vfs);
|
||||
num_vfs = total;
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue