]> Pileus Git - ~andy/linux/commitdiff
sfc: Refactor efx_mcdi_rpc_start() and efx_mcdi_copyin()
authorBen Hutchings <bhutchings@solarflare.com>
Thu, 22 Aug 2013 21:06:09 +0000 (22:06 +0100)
committerBen Hutchings <bhutchings@solarflare.com>
Thu, 29 Aug 2013 17:12:03 +0000 (18:12 +0100)
Preparation for asynchronous MCDI requests.

Signed-off-by: Ben Hutchings <bhutchings@solarflare.com>
drivers/net/ethernet/sfc/mcdi.c

index 63121adbc3bbfdcf777e851bac98d111d5136e48..89bc194a55f7b74b233b086d4f00d277a150f5d0 100644 (file)
@@ -70,8 +70,8 @@ void efx_mcdi_fini(struct efx_nic *efx)
        kfree(efx->mcdi);
 }
 
-static void efx_mcdi_copyin(struct efx_nic *efx, unsigned cmd,
-                           const efx_dword_t *inbuf, size_t inlen)
+static void efx_mcdi_send_request(struct efx_nic *efx, unsigned cmd,
+                                 const efx_dword_t *inbuf, size_t inlen)
 {
        struct efx_mcdi_iface *mcdi = efx_mcdi(efx);
        efx_dword_t hdr[2];
@@ -80,6 +80,11 @@ static void efx_mcdi_copyin(struct efx_nic *efx, unsigned cmd,
 
        BUG_ON(atomic_read(&mcdi->state) == MCDI_STATE_QUIESCENT);
 
+       /* Serialise with efx_mcdi_ev_cpl() and efx_mcdi_ev_death() */
+       spin_lock_bh(&mcdi->iface_lock);
+       ++mcdi->seqno;
+       spin_unlock_bh(&mcdi->iface_lock);
+
        seqno = mcdi->seqno & SEQ_MASK;
        xflags = 0;
        if (mcdi->mode == MCDI_MODE_EVENTS)
@@ -114,6 +119,8 @@ static void efx_mcdi_copyin(struct efx_nic *efx, unsigned cmd,
        }
 
        efx->type->mcdi_request(efx, hdr, hdr_len, inbuf, inlen);
+
+       mcdi->new_epoch = false;
 }
 
 static int efx_mcdi_errno(unsigned int mcdi_err)
@@ -340,6 +347,22 @@ static void efx_mcdi_ev_cpl(struct efx_nic *efx, unsigned int seqno,
                efx_mcdi_complete(mcdi);
 }
 
+static int
+efx_mcdi_check_supported(struct efx_nic *efx, unsigned int cmd, size_t inlen)
+{
+       if (efx->type->mcdi_max_ver < 0 ||
+            (efx->type->mcdi_max_ver < 2 &&
+             cmd > MC_CMD_CMD_SPACE_ESCAPE_7))
+               return -EINVAL;
+
+       if (inlen > MCDI_CTL_SDU_LEN_MAX_V2 ||
+           (efx->type->mcdi_max_ver < 2 &&
+            inlen > MCDI_CTL_SDU_LEN_MAX_V1))
+               return -EMSGSIZE;
+
+       return 0;
+}
+
 int efx_mcdi_rpc(struct efx_nic *efx, unsigned cmd,
                 const efx_dword_t *inbuf, size_t inlen,
                 efx_dword_t *outbuf, size_t outlen,
@@ -358,26 +381,14 @@ int efx_mcdi_rpc_start(struct efx_nic *efx, unsigned cmd,
                       const efx_dword_t *inbuf, size_t inlen)
 {
        struct efx_mcdi_iface *mcdi = efx_mcdi(efx);
+       int rc;
 
-       if (efx->type->mcdi_max_ver < 0 ||
-            (efx->type->mcdi_max_ver < 2 &&
-             cmd > MC_CMD_CMD_SPACE_ESCAPE_7))
-               return -EINVAL;
-
-       if (inlen > MCDI_CTL_SDU_LEN_MAX_V2 ||
-           (efx->type->mcdi_max_ver < 2 &&
-            inlen > MCDI_CTL_SDU_LEN_MAX_V1))
-               return -EMSGSIZE;
+       rc = efx_mcdi_check_supported(efx, cmd, inlen);
+       if (rc)
+               return rc;
 
        efx_mcdi_acquire(mcdi);
-
-       /* Serialise with efx_mcdi_ev_cpl() and efx_mcdi_ev_death() */
-       spin_lock_bh(&mcdi->iface_lock);
-       ++mcdi->seqno;
-       spin_unlock_bh(&mcdi->iface_lock);
-
-       efx_mcdi_copyin(efx, cmd, inbuf, inlen);
-       mcdi->new_epoch = false;
+       efx_mcdi_send_request(efx, cmd, inbuf, inlen);
        return 0;
 }