[DCCP] feat: Actually change the CCID upon negotiation
Change the CCID upon successful feature negotiation. Commiter note: patch mostly rewritten to use the new ccid API. Signed-off-by: Andrea Bittau <a.bittau@cs.ucl.ac.uk> Signed-off-by: Arnaldo Carvalho de Melo <acme@mandriva.com> Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
parent
91f0ebf7b6
commit
6ffd30fbbb
|
@ -14,6 +14,7 @@
|
|||
#include <linux/module.h>
|
||||
|
||||
#include "dccp.h"
|
||||
#include "ccid.h"
|
||||
#include "feat.h"
|
||||
|
||||
#define DCCP_FEAT_SP_NOAGREE (-123)
|
||||
|
@ -26,6 +27,8 @@ int dccp_feat_change(struct sock *sk, u8 type, u8 feature, u8 *val, u8 len,
|
|||
|
||||
dccp_pr_debug("feat change type=%d feat=%d\n", type, feature);
|
||||
|
||||
/* XXX sanity check feat change request */
|
||||
|
||||
/* check if that feature is already being negotiated */
|
||||
list_for_each_entry(opt, &dp->dccps_options.dccpo_pending,
|
||||
dccpop_node) {
|
||||
|
@ -62,11 +65,49 @@ int dccp_feat_change(struct sock *sk, u8 type, u8 feature, u8 *val, u8 len,
|
|||
|
||||
EXPORT_SYMBOL_GPL(dccp_feat_change);
|
||||
|
||||
static int dccp_feat_update_ccid(struct sock *sk, u8 type, u8 new_ccid_nr)
|
||||
{
|
||||
struct dccp_sock *dp = dccp_sk(sk);
|
||||
/* figure out if we are changing our CCID or the peer's */
|
||||
const int rx = type == DCCPO_CHANGE_R;
|
||||
const u8 ccid_nr = rx ? dp->dccps_options.dccpo_rx_ccid :
|
||||
dp->dccps_options.dccpo_tx_ccid;
|
||||
struct ccid *new_ccid;
|
||||
|
||||
/* Check if nothing is being changed. */
|
||||
if (ccid_nr == new_ccid_nr)
|
||||
return 0;
|
||||
|
||||
new_ccid = ccid_new(new_ccid_nr, sk, rx, GFP_ATOMIC);
|
||||
if (new_ccid == NULL)
|
||||
return -ENOMEM;
|
||||
|
||||
if (rx) {
|
||||
ccid_hc_rx_delete(dp->dccps_hc_rx_ccid, sk);
|
||||
dp->dccps_hc_rx_ccid = new_ccid;
|
||||
dp->dccps_options.dccpo_rx_ccid = new_ccid_nr;
|
||||
} else {
|
||||
ccid_hc_tx_delete(dp->dccps_hc_tx_ccid, sk);
|
||||
dp->dccps_hc_tx_ccid = new_ccid;
|
||||
dp->dccps_options.dccpo_tx_ccid = new_ccid_nr;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* XXX taking only u8 vals */
|
||||
static int dccp_feat_update(struct sock *sk, u8 type, u8 feat, u8 val)
|
||||
{
|
||||
/* FIXME implement */
|
||||
dccp_pr_debug("changing [%d] feat %d to %d\n", type, feat, val);
|
||||
|
||||
switch (feat) {
|
||||
case DCCPF_CCID:
|
||||
return dccp_feat_update_ccid(sk, type, val);
|
||||
default:
|
||||
dccp_pr_debug("IMPLEMENT changing [%d] feat %d to %d\n",
|
||||
type, feat, val);
|
||||
break;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue