]> asedeno.scripts.mit.edu Git - linux.git/blobdiff - net/smc/smc_cdc.h
Merge tag 'sound-4.20-rc5' of git://git.kernel.org/pub/scm/linux/kernel/git/tiwai/sound
[linux.git] / net / smc / smc_cdc.h
index f60082fee5b8750c92a6c5f9dfa69d9a2d151ce6..b5bfe38c7f9b6a87258adc0aecce58c31c2a164a 100644 (file)
@@ -48,7 +48,31 @@ struct smc_cdc_msg {
        struct smc_cdc_producer_flags   prod_flags;
        struct smc_cdc_conn_state_flags conn_state_flags;
        u8                              reserved[18];
-} __packed;                                    /* format defined in RFC7609 */
+};
+
+/* SMC-D cursor format */
+union smcd_cdc_cursor {
+       struct {
+               u16     wrap;
+               u32     count;
+               struct smc_cdc_producer_flags   prod_flags;
+               struct smc_cdc_conn_state_flags conn_state_flags;
+       } __packed;
+#ifdef KERNEL_HAS_ATOMIC64
+       atomic64_t              acurs;          /* for atomic processing */
+#else
+       u64                     acurs;          /* for atomic processing */
+#endif
+} __aligned(8);
+
+/* CDC message for SMC-D */
+struct smcd_cdc_msg {
+       struct smc_wr_rx_hdr common;    /* Type = 0xFE */
+       u8 res1[7];
+       union smcd_cdc_cursor   prod;
+       union smcd_cdc_cursor   cons;
+       u8 res3[8];
+} __aligned(8);
 
 static inline bool smc_cdc_rxed_any_close(struct smc_connection *conn)
 {
@@ -90,47 +114,49 @@ static inline u64 smc_curs_read(union smc_host_cursor *curs,
 #endif
 }
 
-static inline u64 smc_curs_read_net(union smc_cdc_cursor *curs,
-                                   struct smc_connection *conn)
+/* Copy cursor src into tgt */
+static inline void smc_curs_copy(union smc_host_cursor *tgt,
+                                union smc_host_cursor *src,
+                                struct smc_connection *conn)
 {
 #ifndef KERNEL_HAS_ATOMIC64
        unsigned long flags;
-       u64 ret;
 
        spin_lock_irqsave(&conn->acurs_lock, flags);
-       ret = curs->acurs;
+       tgt->acurs = src->acurs;
        spin_unlock_irqrestore(&conn->acurs_lock, flags);
-       return ret;
 #else
-       return atomic64_read(&curs->acurs);
+       atomic64_set(&tgt->acurs, atomic64_read(&src->acurs));
 #endif
 }
 
-static inline void smc_curs_write(union smc_host_cursor *curs, u64 val,
-                                 struct smc_connection *conn)
+static inline void smc_curs_copy_net(union smc_cdc_cursor *tgt,
+                                    union smc_cdc_cursor *src,
+                                    struct smc_connection *conn)
 {
 #ifndef KERNEL_HAS_ATOMIC64
        unsigned long flags;
 
        spin_lock_irqsave(&conn->acurs_lock, flags);
-       curs->acurs = val;
+       tgt->acurs = src->acurs;
        spin_unlock_irqrestore(&conn->acurs_lock, flags);
 #else
-       atomic64_set(&curs->acurs, val);
+       atomic64_set(&tgt->acurs, atomic64_read(&src->acurs));
 #endif
 }
 
-static inline void smc_curs_write_net(union smc_cdc_cursor *curs, u64 val,
-                                     struct smc_connection *conn)
+static inline void smcd_curs_copy(union smcd_cdc_cursor *tgt,
+                                 union smcd_cdc_cursor *src,
+                                 struct smc_connection *conn)
 {
 #ifndef KERNEL_HAS_ATOMIC64
        unsigned long flags;
 
        spin_lock_irqsave(&conn->acurs_lock, flags);
-       curs->acurs = val;
+       tgt->acurs = src->acurs;
        spin_unlock_irqrestore(&conn->acurs_lock, flags);
 #else
-       atomic64_set(&curs->acurs, val);
+       atomic64_set(&tgt->acurs, atomic64_read(&src->acurs));
 #endif
 }
 
@@ -165,7 +191,7 @@ static inline void smc_host_cursor_to_cdc(union smc_cdc_cursor *peer,
 {
        union smc_host_cursor temp;
 
-       smc_curs_write(&temp, smc_curs_read(local, conn), conn);
+       smc_curs_copy(&temp, local, conn);
        peer->count = htonl(temp.count);
        peer->wrap = htons(temp.wrap);
        /* peer->reserved = htons(0); must be ensured by caller */
@@ -192,8 +218,8 @@ static inline void smc_cdc_cursor_to_host(union smc_host_cursor *local,
        union smc_host_cursor temp, old;
        union smc_cdc_cursor net;
 
-       smc_curs_write(&old, smc_curs_read(local, conn), conn);
-       smc_curs_write_net(&net, smc_curs_read_net(peer, conn), conn);
+       smc_curs_copy(&old, local, conn);
+       smc_curs_copy_net(&net, peer, conn);
        temp.count = ntohl(net.count);
        temp.wrap = ntohs(net.wrap);
        if ((old.wrap > temp.wrap) && temp.wrap)
@@ -201,12 +227,12 @@ static inline void smc_cdc_cursor_to_host(union smc_host_cursor *local,
        if ((old.wrap == temp.wrap) &&
            (old.count > temp.count))
                return;
-       smc_curs_write(local, smc_curs_read(&temp, conn), conn);
+       smc_curs_copy(local, &temp, conn);
 }
 
-static inline void smc_cdc_msg_to_host(struct smc_host_cdc_msg *local,
-                                      struct smc_cdc_msg *peer,
-                                      struct smc_connection *conn)
+static inline void smcr_cdc_msg_to_host(struct smc_host_cdc_msg *local,
+                                       struct smc_cdc_msg *peer,
+                                       struct smc_connection *conn)
 {
        local->common.type = peer->common.type;
        local->len = peer->len;
@@ -218,6 +244,32 @@ static inline void smc_cdc_msg_to_host(struct smc_host_cdc_msg *local,
        local->conn_state_flags = peer->conn_state_flags;
 }
 
+static inline void smcd_cdc_msg_to_host(struct smc_host_cdc_msg *local,
+                                       struct smcd_cdc_msg *peer)
+{
+       union smc_host_cursor temp;
+
+       temp.wrap = peer->prod.wrap;
+       temp.count = peer->prod.count;
+       atomic64_set(&local->prod.acurs, atomic64_read(&temp.acurs));
+
+       temp.wrap = peer->cons.wrap;
+       temp.count = peer->cons.count;
+       atomic64_set(&local->cons.acurs, atomic64_read(&temp.acurs));
+       local->prod_flags = peer->cons.prod_flags;
+       local->conn_state_flags = peer->cons.conn_state_flags;
+}
+
+static inline void smc_cdc_msg_to_host(struct smc_host_cdc_msg *local,
+                                      struct smc_cdc_msg *peer,
+                                      struct smc_connection *conn)
+{
+       if (conn->lgr->is_smcd)
+               smcd_cdc_msg_to_host(local, (struct smcd_cdc_msg *)peer);
+       else
+               smcr_cdc_msg_to_host(local, peer, conn);
+}
+
 struct smc_cdc_tx_pend;
 
 int smc_cdc_get_free_slot(struct smc_connection *conn,
@@ -227,6 +279,8 @@ void smc_cdc_tx_dismiss_slots(struct smc_connection *conn);
 int smc_cdc_msg_send(struct smc_connection *conn, struct smc_wr_buf *wr_buf,
                     struct smc_cdc_tx_pend *pend);
 int smc_cdc_get_slot_and_msg_send(struct smc_connection *conn);
+int smcd_cdc_msg_send(struct smc_connection *conn);
 int smc_cdc_init(void) __init;
+void smcd_cdc_rx_init(struct smc_connection *conn);
 
 #endif /* SMC_CDC_H */