]> git.karo-electronics.de Git - karo-tx-linux.git/commitdiff
drbd: Implemented receiving of new style packets on meta socket
authorPhilipp Reisner <philipp.reisner@linbit.com>
Wed, 26 Jan 2011 11:15:29 +0000 (12:15 +0100)
committerPhilipp Reisner <philipp.reisner@linbit.com>
Wed, 28 Sep 2011 08:26:18 +0000 (10:26 +0200)
Now drbd communication with protocol 100 actually works.
Replaced the remaining p_header80 with p_header where we
no longer know which header it is.

In the places where p_header80 is still in use, it is on
purpose, because we know that it is an old style header
there.

Signed-off-by: Philipp Reisner <philipp.reisner@linbit.com>
Signed-off-by: Lars Ellenberg <lars.ellenberg@linbit.com>
drivers/block/drbd/drbd_receiver.c

index 8f5a241fe20aa44921e18be728228009792c5063..c0435c4f5d84d81cb04f04c4cae694bdaef15ed1 100644 (file)
@@ -926,18 +926,9 @@ out_release_sockets:
        return -1;
 }
 
-static int drbd_recv_header(struct drbd_conf *mdev, enum drbd_packets *cmd, unsigned int *packet_size)
+static bool decode_header(struct drbd_conf *mdev, struct p_header *h, enum drbd_packets *cmd,
+                         unsigned int *packet_size)
 {
-       struct p_header *h = &mdev->tconn->data.rbuf.header;
-       int r;
-
-       r = drbd_recv(mdev, h, sizeof(*h));
-       if (unlikely(r != sizeof(*h))) {
-               if (!signal_pending(current))
-                       dev_warn(DEV, "short read expecting header on sock: r=%d\n", r);
-               return false;
-       }
-
        if (h->h80.magic == cpu_to_be32(DRBD_MAGIC)) {
                *cmd = be16_to_cpu(h->h80.command);
                *packet_size = be16_to_cpu(h->h80.length);
@@ -951,9 +942,25 @@ static int drbd_recv_header(struct drbd_conf *mdev, enum drbd_packets *cmd, unsi
                    be16_to_cpu(h->h80.length));
                return false;
        }
+       return true;
+}
+
+static int drbd_recv_header(struct drbd_conf *mdev, enum drbd_packets *cmd, unsigned int *packet_size)
+{
+       struct p_header *h = &mdev->tconn->data.rbuf.header;
+       int r;
+
+       r = drbd_recv(mdev, h, sizeof(*h));
+       if (unlikely(r != sizeof(*h))) {
+               if (!signal_pending(current))
+                       dev_warn(DEV, "short read expecting header on sock: r=%d\n", r);
+               return false;
+       }
+
+       r = decode_header(mdev, h, cmd, packet_size);
        mdev->tconn->last_received = jiffies;
 
-       return true;
+       return r;
 }
 
 static void drbd_flush(struct drbd_conf *mdev)
@@ -2807,14 +2814,14 @@ static int receive_SyncParam(struct drbd_conf *mdev, enum drbd_packets cmd, unsi
        }
 
        if (apv <= 88) {
-               header_size = sizeof(struct p_rs_param) - sizeof(struct p_header80);
+               header_size = sizeof(struct p_rs_param) - sizeof(struct p_header);
                data_size   = packet_size  - header_size;
        } else if (apv <= 94) {
-               header_size = sizeof(struct p_rs_param_89) - sizeof(struct p_header80);
+               header_size = sizeof(struct p_rs_param_89) - sizeof(struct p_header);
                data_size   = packet_size  - header_size;
                D_ASSERT(data_size == 0);
        } else {
-               header_size = sizeof(struct p_rs_param_95) - sizeof(struct p_header80);
+               header_size = sizeof(struct p_rs_param_95) - sizeof(struct p_header);
                data_size   = packet_size  - header_size;
                D_ASSERT(data_size == 0);
        }
@@ -3524,7 +3531,7 @@ static int receive_bitmap(struct drbd_conf *mdev, enum drbd_packets cmd, unsigne
        void *buffer;
        int err;
        int ok = false;
-       struct p_header80 *h = &mdev->tconn->data.rbuf.header.h80;
+       struct p_header *h = &mdev->tconn->data.rbuf.header;
 
        drbd_bm_lock(mdev, "receive bitmap", BM_LOCKED_SET_ALLOWED);
        /* you are supposed to send additional out-of-sync information
@@ -3571,7 +3578,7 @@ static int receive_bitmap(struct drbd_conf *mdev, enum drbd_packets cmd, unsigne
                }
 
                c.packets[cmd == P_BITMAP]++;
-               c.bytes[cmd == P_BITMAP] += sizeof(struct p_header80) + data_size;
+               c.bytes[cmd == P_BITMAP] += sizeof(struct p_header) + data_size;
 
                if (err <= 0) {
                        if (err < 0)
@@ -3670,13 +3677,13 @@ static struct data_cmd drbd_cmd_handler[] = {
        [P_DATA_REPLY]      = { 1, sizeof(struct p_data), receive_DataReply },
        [P_RS_DATA_REPLY]   = { 1, sizeof(struct p_data), receive_RSDataReply } ,
        [P_BARRIER]         = { 0, sizeof(struct p_barrier), receive_Barrier } ,
-       [P_BITMAP]          = { 1, sizeof(struct p_header80), receive_bitmap } ,
-       [P_COMPRESSED_BITMAP] = { 1, sizeof(struct p_header80), receive_bitmap } ,
-       [P_UNPLUG_REMOTE]   = { 0, sizeof(struct p_header80), receive_UnplugRemote },
+       [P_BITMAP]          = { 1, sizeof(struct p_header), receive_bitmap } ,
+       [P_COMPRESSED_BITMAP] = { 1, sizeof(struct p_header), receive_bitmap } ,
+       [P_UNPLUG_REMOTE]   = { 0, sizeof(struct p_header), receive_UnplugRemote },
        [P_DATA_REQUEST]    = { 0, sizeof(struct p_block_req), receive_DataRequest },
        [P_RS_DATA_REQUEST] = { 0, sizeof(struct p_block_req), receive_DataRequest },
-       [P_SYNC_PARAM]      = { 1, sizeof(struct p_header80), receive_SyncParam },
-       [P_SYNC_PARAM89]    = { 1, sizeof(struct p_header80), receive_SyncParam },
+       [P_SYNC_PARAM]      = { 1, sizeof(struct p_header), receive_SyncParam },
+       [P_SYNC_PARAM89]    = { 1, sizeof(struct p_header), receive_SyncParam },
        [P_PROTOCOL]        = { 1, sizeof(struct p_protocol), receive_protocol },
        [P_UUIDS]           = { 0, sizeof(struct p_uuids), receive_uuids },
        [P_SIZES]           = { 0, sizeof(struct p_sizes), receive_sizes },
@@ -4184,9 +4191,9 @@ int drbdd_init(struct drbd_thread *thi)
 
 /* ********* acknowledge sender ******** */
 
-static int got_RqSReply(struct drbd_conf *mdev, struct p_header80 *h)
+static int got_RqSReply(struct drbd_conf *mdev, enum drbd_packets cmd)
 {
-       struct p_req_state_reply *p = (struct p_req_state_reply *)h;
+       struct p_req_state_reply *p = &mdev->tconn->meta.rbuf.req_state_reply;
 
        int retcode = be32_to_cpu(p->retcode);
 
@@ -4202,13 +4209,13 @@ static int got_RqSReply(struct drbd_conf *mdev, struct p_header80 *h)
        return true;
 }
 
-static int got_Ping(struct drbd_conf *mdev, struct p_header80 *h)
+static int got_Ping(struct drbd_conf *mdev, enum drbd_packets cmd)
 {
        return drbd_send_ping_ack(mdev);
 
 }
 
-static int got_PingAck(struct drbd_conf *mdev, struct p_header80 *h)
+static int got_PingAck(struct drbd_conf *mdev, enum drbd_packets cmd)
 {
        /* restore idle timeout */
        mdev->tconn->meta.socket->sk->sk_rcvtimeo = mdev->tconn->net_conf->ping_int*HZ;
@@ -4218,9 +4225,9 @@ static int got_PingAck(struct drbd_conf *mdev, struct p_header80 *h)
        return true;
 }
 
-static int got_IsInSync(struct drbd_conf *mdev, struct p_header80 *h)
+static int got_IsInSync(struct drbd_conf *mdev, enum drbd_packets cmd)
 {
-       struct p_block_ack *p = (struct p_block_ack *)h;
+       struct p_block_ack *p = &mdev->tconn->meta.rbuf.block_ack;
        sector_t sector = be64_to_cpu(p->sector);
        int blksize = be32_to_cpu(p->blksize);
 
@@ -4263,9 +4270,9 @@ validate_req_change_req_state(struct drbd_conf *mdev, u64 id, sector_t sector,
        return true;
 }
 
-static int got_BlockAck(struct drbd_conf *mdev, struct p_header80 *h)
+static int got_BlockAck(struct drbd_conf *mdev, enum drbd_packets cmd)
 {
-       struct p_block_ack *p = (struct p_block_ack *)h;
+       struct p_block_ack *p = &mdev->tconn->meta.rbuf.block_ack;
        sector_t sector = be64_to_cpu(p->sector);
        int blksize = be32_to_cpu(p->blksize);
        enum drbd_req_event what;
@@ -4277,7 +4284,7 @@ static int got_BlockAck(struct drbd_conf *mdev, struct p_header80 *h)
                dec_rs_pending(mdev);
                return true;
        }
-       switch (be16_to_cpu(h->command)) {
+       switch (cmd) {
        case P_RS_WRITE_ACK:
                D_ASSERT(mdev->tconn->net_conf->wire_protocol == DRBD_PROT_C);
                what = WRITE_ACKED_BY_PEER_AND_SIS;
@@ -4304,9 +4311,9 @@ static int got_BlockAck(struct drbd_conf *mdev, struct p_header80 *h)
                                             what, false);
 }
 
-static int got_NegAck(struct drbd_conf *mdev, struct p_header80 *h)
+static int got_NegAck(struct drbd_conf *mdev, enum drbd_packets cmd)
 {
-       struct p_block_ack *p = (struct p_block_ack *)h;
+       struct p_block_ack *p = &mdev->tconn->meta.rbuf.block_ack;
        sector_t sector = be64_to_cpu(p->sector);
        int size = be32_to_cpu(p->blksize);
        bool missing_ok = mdev->tconn->net_conf->wire_protocol == DRBD_PROT_A ||
@@ -4337,9 +4344,9 @@ static int got_NegAck(struct drbd_conf *mdev, struct p_header80 *h)
        return true;
 }
 
-static int got_NegDReply(struct drbd_conf *mdev, struct p_header80 *h)
+static int got_NegDReply(struct drbd_conf *mdev, enum drbd_packets cmd)
 {
-       struct p_block_ack *p = (struct p_block_ack *)h;
+       struct p_block_ack *p = &mdev->tconn->meta.rbuf.block_ack;
        sector_t sector = be64_to_cpu(p->sector);
 
        update_peer_seq(mdev, be32_to_cpu(p->seq_num));
@@ -4351,11 +4358,11 @@ static int got_NegDReply(struct drbd_conf *mdev, struct p_header80 *h)
                                             NEG_ACKED, false);
 }
 
-static int got_NegRSDReply(struct drbd_conf *mdev, struct p_header80 *h)
+static int got_NegRSDReply(struct drbd_conf *mdev, enum drbd_packets cmd)
 {
        sector_t sector;
        int size;
-       struct p_block_ack *p = (struct p_block_ack *)h;
+       struct p_block_ack *p = &mdev->tconn->meta.rbuf.block_ack;
 
        sector = be64_to_cpu(p->sector);
        size = be32_to_cpu(p->blksize);
@@ -4366,7 +4373,7 @@ static int got_NegRSDReply(struct drbd_conf *mdev, struct p_header80 *h)
 
        if (get_ldev_if_state(mdev, D_FAILED)) {
                drbd_rs_complete_io(mdev, sector);
-               switch (be16_to_cpu(h->command)) {
+               switch (cmd) {
                case P_NEG_RS_DREPLY:
                        drbd_rs_failed_io(mdev, sector, size);
                case P_RS_CANCEL:
@@ -4382,9 +4389,9 @@ static int got_NegRSDReply(struct drbd_conf *mdev, struct p_header80 *h)
        return true;
 }
 
-static int got_BarrierAck(struct drbd_conf *mdev, struct p_header80 *h)
+static int got_BarrierAck(struct drbd_conf *mdev, enum drbd_packets cmd)
 {
-       struct p_barrier_ack *p = (struct p_barrier_ack *)h;
+       struct p_barrier_ack *p = &mdev->tconn->meta.rbuf.barrier_ack;
 
        tl_release(mdev, p->barrier, be32_to_cpu(p->set_size));
 
@@ -4398,9 +4405,9 @@ static int got_BarrierAck(struct drbd_conf *mdev, struct p_header80 *h)
        return true;
 }
 
-static int got_OVResult(struct drbd_conf *mdev, struct p_header80 *h)
+static int got_OVResult(struct drbd_conf *mdev, enum drbd_packets cmd)
 {
-       struct p_block_ack *p = (struct p_block_ack *)h;
+       struct p_block_ack *p = &mdev->tconn->meta.rbuf.block_ack;
        struct drbd_work *w;
        sector_t sector;
        int size;
@@ -4442,14 +4449,14 @@ static int got_OVResult(struct drbd_conf *mdev, struct p_header80 *h)
        return true;
 }
 
-static int got_skip(struct drbd_conf *mdev, struct p_header80 *h)
+static int got_skip(struct drbd_conf *mdev, enum drbd_packets cmd)
 {
        return true;
 }
 
 struct asender_cmd {
        size_t pkt_size;
-       int (*process)(struct drbd_conf *mdev, struct p_header80 *h);
+       int (*process)(struct drbd_conf *mdev, enum drbd_packets cmd);
 };
 
 static struct asender_cmd *get_asender_cmd(int cmd)
@@ -4458,8 +4465,8 @@ static struct asender_cmd *get_asender_cmd(int cmd)
                /* anything missing from this table is in
                 * the drbd_cmd_handler (drbd_default_handler) table,
                 * see the beginning of drbdd() */
-       [P_PING]            = { sizeof(struct p_header80), got_Ping },
-       [P_PING_ACK]        = { sizeof(struct p_header80), got_PingAck },
+       [P_PING]            = { sizeof(struct p_header), got_Ping },
+       [P_PING_ACK]        = { sizeof(struct p_header), got_PingAck },
        [P_RECV_ACK]        = { sizeof(struct p_block_ack), got_BlockAck },
        [P_WRITE_ACK]       = { sizeof(struct p_block_ack), got_BlockAck },
        [P_RS_WRITE_ACK]    = { sizeof(struct p_block_ack), got_BlockAck },
@@ -4483,15 +4490,16 @@ static struct asender_cmd *get_asender_cmd(int cmd)
 int drbd_asender(struct drbd_thread *thi)
 {
        struct drbd_conf *mdev = thi->mdev;
-       struct p_header80 *h = &mdev->tconn->meta.rbuf.header.h80;
+       struct p_header *h = &mdev->tconn->meta.rbuf.header;
        struct asender_cmd *cmd = NULL;
 
-       int rv, len;
+       int rv;
        void *buf    = h;
        int received = 0;
-       int expect   = sizeof(struct p_header80);
-       int empty;
+       int expect   = sizeof(struct p_header);
        int ping_timeout_active = 0;
+       int empty, pkt_size;
+       enum drbd_packets cmd_nr;
 
        sprintf(current->comm, "drbd%d_asender", mdev_to_minor(mdev));
 
@@ -4581,30 +4589,25 @@ int drbd_asender(struct drbd_thread *thi)
                }
 
                if (received == expect && cmd == NULL) {
-                       if (unlikely(h->magic != cpu_to_be32(DRBD_MAGIC))) {
-                               dev_err(DEV, "magic?? on meta m: 0x%08x c: %d l: %d\n",
-                                   be32_to_cpu(h->magic),
-                                   be16_to_cpu(h->command),
-                                   be16_to_cpu(h->length));
+                       if (!decode_header(mdev, h, &cmd_nr, &pkt_size))
                                goto reconnect;
-                       }
-                       cmd = get_asender_cmd(be16_to_cpu(h->command));
-                       len = be16_to_cpu(h->length);
+                       cmd = get_asender_cmd(cmd_nr);
                        if (unlikely(cmd == NULL)) {
-                               dev_err(DEV, "unknown command?? on meta m: 0x%08x c: %d l: %d\n",
-                                   be32_to_cpu(h->magic),
-                                   be16_to_cpu(h->command),
-                                   be16_to_cpu(h->length));
+                               dev_err(DEV, "unknown command %d on meta (l: %d)\n",
+                                       cmd_nr, pkt_size);
                                goto disconnect;
                        }
                        expect = cmd->pkt_size;
-                       if (!expect(len == expect - sizeof(struct p_header80)))
+                       if (pkt_size != expect - sizeof(struct p_header)) {
+                               dev_err(DEV, "Wrong packet size on meta (c: %d, l: %d)\n",
+                                       cmd_nr, pkt_size);
                                goto reconnect;
+                       }
                }
                if (received == expect) {
                        mdev->tconn->last_received = jiffies;
                        D_ASSERT(cmd != NULL);
-                       if (!cmd->process(mdev, h))
+                       if (!cmd->process(mdev, cmd_nr))
                                goto reconnect;
 
                        /* the idle_timeout (ping-int)
@@ -4614,7 +4617,7 @@ int drbd_asender(struct drbd_thread *thi)
 
                        buf      = h;
                        received = 0;
-                       expect   = sizeof(struct p_header80);
+                       expect   = sizeof(struct p_header);
                        cmd      = NULL;
                }
        }