diff --git a/[refs] b/[refs] index e069883d7658..1c4631df95e7 100644 --- a/[refs] +++ b/[refs] @@ -1,2 +1,2 @@ --- -refs/heads/master: 4880d10927c93d858d40e297361fff375ee98492 +refs/heads/master: 78ab88f04f44bed566d51dce0c7cbfeff6449a06 diff --git a/trunk/drivers/ata/ahci.c b/trunk/drivers/ata/ahci.c index 8cace9aa9c03..97f83fb2ee2e 100644 --- a/trunk/drivers/ata/ahci.c +++ b/trunk/drivers/ata/ahci.c @@ -1267,9 +1267,7 @@ static int ahci_check_ready(struct ata_link *link) void __iomem *port_mmio = ahci_port_base(link->ap); u8 status = readl(port_mmio + PORT_TFDATA) & 0xFF; - if (!(status & ATA_BUSY)) - return 1; - return 0; + return ata_check_ready(status); } static int ahci_softreset(struct ata_link *link, unsigned int *class, diff --git a/trunk/drivers/ata/libata-sff.c b/trunk/drivers/ata/libata-sff.c index 2ec65a8fda79..3c2d2289f85e 100644 --- a/trunk/drivers/ata/libata-sff.c +++ b/trunk/drivers/ata/libata-sff.c @@ -314,11 +314,7 @@ static int ata_sff_check_ready(struct ata_link *link) { u8 status = link->ap->ops->sff_check_status(link->ap); - if (!(status & ATA_BUSY)) - return 1; - if (status == 0xff) - return -ENODEV; - return 0; + return ata_check_ready(status); } /** diff --git a/trunk/drivers/net/irda/nsc-ircc.c b/trunk/drivers/net/irda/nsc-ircc.c index a7714da7c283..a873d2b315ca 100644 --- a/trunk/drivers/net/irda/nsc-ircc.c +++ b/trunk/drivers/net/irda/nsc-ircc.c @@ -100,9 +100,7 @@ static int nsc_ircc_probe_39x(nsc_chip_t *chip, chipio_t *info); static int nsc_ircc_init_108(nsc_chip_t *chip, chipio_t *info); static int nsc_ircc_init_338(nsc_chip_t *chip, chipio_t *info); static int nsc_ircc_init_39x(nsc_chip_t *chip, chipio_t *info); -#ifdef CONFIG_PNP static int nsc_ircc_pnp_probe(struct pnp_dev *dev, const struct pnp_device_id *id); -#endif /* These are the known NSC chips */ static nsc_chip_t chips[] = { @@ -158,11 +156,9 @@ static const struct pnp_device_id nsc_ircc_pnp_table[] = { MODULE_DEVICE_TABLE(pnp, nsc_ircc_pnp_table); static struct pnp_driver nsc_ircc_pnp_driver = { -#ifdef CONFIG_PNP .name = "nsc-ircc", .id_table = nsc_ircc_pnp_table, .probe = nsc_ircc_pnp_probe, -#endif }; /* Some prototypes */ @@ -920,7 +916,6 @@ static int nsc_ircc_probe_39x(nsc_chip_t *chip, chipio_t *info) return 0; } -#ifdef CONFIG_PNP /* PNP probing */ static int nsc_ircc_pnp_probe(struct pnp_dev *dev, const struct pnp_device_id *id) { @@ -957,7 +952,6 @@ static int nsc_ircc_pnp_probe(struct pnp_dev *dev, const struct pnp_device_id *i return 0; } -#endif /* * Function nsc_ircc_setup (info) diff --git a/trunk/drivers/net/irda/smsc-ircc2.c b/trunk/drivers/net/irda/smsc-ircc2.c index cfe0194fef71..1f26da761e9f 100644 --- a/trunk/drivers/net/irda/smsc-ircc2.c +++ b/trunk/drivers/net/irda/smsc-ircc2.c @@ -376,7 +376,6 @@ MODULE_DEVICE_TABLE(pnp, smsc_ircc_pnp_table); static int pnp_driver_registered; -#ifdef CONFIG_PNP static int __init smsc_ircc_pnp_probe(struct pnp_dev *dev, const struct pnp_device_id *dev_id) { @@ -403,9 +402,7 @@ static struct pnp_driver smsc_ircc_pnp_driver = { .id_table = smsc_ircc_pnp_table, .probe = smsc_ircc_pnp_probe, }; -#else /* CONFIG_PNP */ -static struct pnp_driver smsc_ircc_pnp_driver; -#endif + /******************************************************************************* * diff --git a/trunk/drivers/net/niu.c b/trunk/drivers/net/niu.c index 57cfd72ffdf7..4009c4ce96b4 100644 --- a/trunk/drivers/net/niu.c +++ b/trunk/drivers/net/niu.c @@ -1,6 +1,6 @@ /* niu.c: Neptune ethernet driver. * - * Copyright (C) 2007, 2008 David S. Miller (davem@davemloft.net) + * Copyright (C) 2007 David S. Miller (davem@davemloft.net) */ #include @@ -33,8 +33,8 @@ #define DRV_MODULE_NAME "niu" #define PFX DRV_MODULE_NAME ": " -#define DRV_MODULE_VERSION "0.9" -#define DRV_MODULE_RELDATE "May 4, 2008" +#define DRV_MODULE_VERSION "0.8" +#define DRV_MODULE_RELDATE "April 24, 2008" static char version[] __devinitdata = DRV_MODULE_NAME ".c:v" DRV_MODULE_VERSION " (" DRV_MODULE_RELDATE ")\n"; @@ -7264,11 +7264,8 @@ static int __devinit niu_get_and_validate_port(struct niu *np) parent->num_ports = nr64(ESPC_NUM_PORTS_MACS) & ESPC_NUM_PORTS_MACS_VAL; - /* All of the current probing methods fail on - * Maramba on-board parts. - */ if (!parent->num_ports) - parent->num_ports = 4; + return -ENODEV; } } } diff --git a/trunk/drivers/net/wan/lapbether.c b/trunk/drivers/net/wan/lapbether.c index 24fd613466b7..b5860b97a93e 100644 --- a/trunk/drivers/net/wan/lapbether.c +++ b/trunk/drivers/net/wan/lapbether.c @@ -459,7 +459,6 @@ static void __exit lapbeth_cleanup_driver(void) list_for_each_safe(entry, tmp, &lapbeth_devices) { lapbeth = list_entry(entry, struct lapbethdev, node); - dev_put(lapbeth->ethdev); unregister_netdevice(lapbeth->axdev); } rtnl_unlock(); diff --git a/trunk/drivers/net/wireless/iwlwifi/Kconfig b/trunk/drivers/net/wireless/iwlwifi/Kconfig index 62fb89d82318..d5b7a76fcaad 100644 --- a/trunk/drivers/net/wireless/iwlwifi/Kconfig +++ b/trunk/drivers/net/wireless/iwlwifi/Kconfig @@ -1,5 +1,6 @@ config IWLWIFI - tristate + bool + default n config IWLCORE tristate "Intel Wireless Wifi Core" diff --git a/trunk/include/linux/libata.h b/trunk/include/linux/libata.h index d1dfe872ee30..95e6159b44cf 100644 --- a/trunk/include/linux/libata.h +++ b/trunk/include/linux/libata.h @@ -1381,6 +1381,21 @@ static inline struct ata_port *ata_shost_to_port(struct Scsi_Host *host) return *(struct ata_port **)&host->hostdata[0]; } +static inline int ata_check_ready(u8 status) +{ + /* Some controllers report 0x77 or 0x7f during intermediate + * not-ready stages. + */ + if (status == 0x77 || status == 0x7f) + return 0; + + /* 0xff indicates either no device or device not ready */ + if (status == 0xff) + return -ENODEV; + + return !(status & ATA_BUSY); +} + /************************************************************************** * PMP - drivers/ata/libata-pmp.c diff --git a/trunk/include/net/ip.h b/trunk/include/net/ip.h index 3b40bc2234be..6d7bcd5e62d4 100644 --- a/trunk/include/net/ip.h +++ b/trunk/include/net/ip.h @@ -210,7 +210,7 @@ int ip_dont_fragment(struct sock *sk, struct dst_entry *dst) { return (inet_sk(sk)->pmtudisc == IP_PMTUDISC_DO || (inet_sk(sk)->pmtudisc == IP_PMTUDISC_WANT && - !(dst_metric_locked(dst, RTAX_MTU)))); + !(dst_metric(dst, RTAX_LOCK)&(1<brvccs)) { - write_lock_irq(&devs_lock); + read_lock(&devs_lock); list_del(&brdev->br2684_devs); - write_unlock_irq(&devs_lock); + read_unlock(&devs_lock); unregister_netdev(net_dev); free_netdev(net_dev); } diff --git a/trunk/net/bridge/br_if.c b/trunk/net/bridge/br_if.c index c2397f503b0f..77a981a1ee52 100644 --- a/trunk/net/bridge/br_if.c +++ b/trunk/net/bridge/br_if.c @@ -273,13 +273,15 @@ int br_add_bridge(const char *name) rtnl_lock(); if (strchr(dev->name, '%')) { ret = dev_alloc_name(dev, dev->name); - if (ret < 0) - goto out_free; + if (ret < 0) { + free_netdev(dev); + goto out; + } } ret = register_netdevice(dev); if (ret) - goto out_free; + goto out; ret = br_sysfs_addbr(dev); if (ret) @@ -287,10 +289,6 @@ int br_add_bridge(const char *name) out: rtnl_unlock(); return ret; - -out_free: - free_netdev(dev); - goto out; } int br_del_bridge(const char *name) diff --git a/trunk/net/core/skbuff.c b/trunk/net/core/skbuff.c index 5c459f2b7985..4fe605fa6f8a 100644 --- a/trunk/net/core/skbuff.c +++ b/trunk/net/core/skbuff.c @@ -200,9 +200,7 @@ struct sk_buff *__alloc_skb(unsigned int size, gfp_t gfp_mask, goto nodata; /* - * Only clear those fields we need to clear, not those that we will - * actually initialise below. Hence, don't put any more fields after - * the tail pointer in struct sk_buff! + * See comment in sk_buff definition, just before the 'tail' member */ memset(skb, 0, offsetof(struct sk_buff, tail)); skb->truesize = size + sizeof(struct sk_buff); diff --git a/trunk/net/dccp/feat.c b/trunk/net/dccp/feat.c index 933a0ecf8d46..4a4f6ce4498d 100644 --- a/trunk/net/dccp/feat.c +++ b/trunk/net/dccp/feat.c @@ -32,7 +32,7 @@ int dccp_feat_change(struct dccp_minisock *dmsk, u8 type, u8 feature, if (len > 3) { DCCP_WARN("invalid length %d\n", len); - return -EINVAL; + return 1; } /* XXX add further sanity checks */ diff --git a/trunk/net/decnet/dn_route.c b/trunk/net/decnet/dn_route.c index f50e88bf2661..2f665a516476 100644 --- a/trunk/net/decnet/dn_route.c +++ b/trunk/net/decnet/dn_route.c @@ -235,14 +235,14 @@ static void dn_dst_update_pmtu(struct dst_entry *dst, u32 mtu) else min_mtu -= 21; - if (dst_metric(dst, RTAX_MTU) > mtu && mtu >= min_mtu) { + if (dst->metrics[RTAX_MTU-1] > mtu && mtu >= min_mtu) { if (!(dst_metric_locked(dst, RTAX_MTU))) { dst->metrics[RTAX_MTU-1] = mtu; dst_set_expires(dst, dn_rt_mtu_expires); } if (!(dst_metric_locked(dst, RTAX_ADVMSS))) { u32 mss = mtu - DN_MAX_NSP_DATA_HEADER; - if (dst_metric(dst, RTAX_ADVMSS) > mss) + if (dst->metrics[RTAX_ADVMSS-1] > mss) dst->metrics[RTAX_ADVMSS-1] = mss; } } @@ -805,12 +805,12 @@ static int dn_rt_set_next_hop(struct dn_route *rt, struct dn_fib_res *res) rt->u.dst.neighbour = n; } - if (dst_metric(&rt->u.dst, RTAX_MTU) == 0 || - dst_metric(&rt->u.dst, RTAX_MTU) > rt->u.dst.dev->mtu) + if (rt->u.dst.metrics[RTAX_MTU-1] == 0 || + rt->u.dst.metrics[RTAX_MTU-1] > rt->u.dst.dev->mtu) rt->u.dst.metrics[RTAX_MTU-1] = rt->u.dst.dev->mtu; mss = dn_mss_from_pmtu(dev, dst_mtu(&rt->u.dst)); - if (dst_metric(&rt->u.dst, RTAX_ADVMSS) == 0 || - dst_metric(&rt->u.dst, RTAX_ADVMSS) > mss) + if (rt->u.dst.metrics[RTAX_ADVMSS-1] == 0 || + rt->u.dst.metrics[RTAX_ADVMSS-1] > mss) rt->u.dst.metrics[RTAX_ADVMSS-1] = mss; return 0; } diff --git a/trunk/net/ipv4/route.c b/trunk/net/ipv4/route.c index 92f90ae46f4a..5e3685c5c407 100644 --- a/trunk/net/ipv4/route.c +++ b/trunk/net/ipv4/route.c @@ -1468,14 +1468,14 @@ unsigned short ip_rt_frag_needed(struct net *net, struct iphdr *iph, /* BSD 4.2 compatibility hack :-( */ if (mtu == 0 && - old_mtu >= dst_metric(&rth->u.dst, RTAX_MTU) && + old_mtu >= rth->u.dst.metrics[RTAX_MTU-1] && old_mtu >= 68 + (iph->ihl << 2)) old_mtu -= iph->ihl << 2; mtu = guess_mtu(old_mtu); } - if (mtu <= dst_metric(&rth->u.dst, RTAX_MTU)) { - if (mtu < dst_metric(&rth->u.dst, RTAX_MTU)) { + if (mtu <= rth->u.dst.metrics[RTAX_MTU-1]) { + if (mtu < rth->u.dst.metrics[RTAX_MTU-1]) { dst_confirm(&rth->u.dst); if (mtu < ip_rt_min_pmtu) { mtu = ip_rt_min_pmtu; @@ -1497,7 +1497,7 @@ unsigned short ip_rt_frag_needed(struct net *net, struct iphdr *iph, static void ip_rt_update_pmtu(struct dst_entry *dst, u32 mtu) { - if (dst_metric(dst, RTAX_MTU) > mtu && mtu >= 68 && + if (dst->metrics[RTAX_MTU-1] > mtu && mtu >= 68 && !(dst_metric_locked(dst, RTAX_MTU))) { if (mtu < ip_rt_min_pmtu) { mtu = ip_rt_min_pmtu; @@ -1613,7 +1613,7 @@ static void rt_set_nexthop(struct rtable *rt, struct fib_result *res, u32 itag) sizeof(rt->u.dst.metrics)); if (fi->fib_mtu == 0) { rt->u.dst.metrics[RTAX_MTU-1] = rt->u.dst.dev->mtu; - if (dst_metric_locked(&rt->u.dst, RTAX_MTU) && + if (rt->u.dst.metrics[RTAX_LOCK-1] & (1 << RTAX_MTU) && rt->rt_gateway != rt->rt_dst && rt->u.dst.dev->mtu > 576) rt->u.dst.metrics[RTAX_MTU-1] = 576; @@ -1624,14 +1624,14 @@ static void rt_set_nexthop(struct rtable *rt, struct fib_result *res, u32 itag) } else rt->u.dst.metrics[RTAX_MTU-1]= rt->u.dst.dev->mtu; - if (dst_metric(&rt->u.dst, RTAX_HOPLIMIT) == 0) + if (rt->u.dst.metrics[RTAX_HOPLIMIT-1] == 0) rt->u.dst.metrics[RTAX_HOPLIMIT-1] = sysctl_ip_default_ttl; - if (dst_metric(&rt->u.dst, RTAX_MTU) > IP_MAX_MTU) + if (rt->u.dst.metrics[RTAX_MTU-1] > IP_MAX_MTU) rt->u.dst.metrics[RTAX_MTU-1] = IP_MAX_MTU; - if (dst_metric(&rt->u.dst, RTAX_ADVMSS) == 0) + if (rt->u.dst.metrics[RTAX_ADVMSS-1] == 0) rt->u.dst.metrics[RTAX_ADVMSS-1] = max_t(unsigned int, rt->u.dst.dev->mtu - 40, ip_rt_min_advmss); - if (dst_metric(&rt->u.dst, RTAX_ADVMSS) > 65535 - 40) + if (rt->u.dst.metrics[RTAX_ADVMSS-1] > 65535 - 40) rt->u.dst.metrics[RTAX_ADVMSS-1] = 65535 - 40; #ifdef CONFIG_NET_CLS_ROUTE diff --git a/trunk/net/ipv4/tcp_input.c b/trunk/net/ipv4/tcp_input.c index 8ac15a604e08..eda4f4a233f3 100644 --- a/trunk/net/ipv4/tcp_input.c +++ b/trunk/net/ipv4/tcp_input.c @@ -66,7 +66,6 @@ #include #include #include -#include #include #include #include @@ -606,7 +605,7 @@ static u32 tcp_rto_min(struct sock *sk) u32 rto_min = TCP_RTO_MIN; if (dst && dst_metric_locked(dst, RTAX_RTO_MIN)) - rto_min = dst_metric(dst, RTAX_RTO_MIN); + rto_min = dst->metrics[RTAX_RTO_MIN - 1]; return rto_min; } @@ -770,7 +769,7 @@ void tcp_update_metrics(struct sock *sk) dst->metrics[RTAX_RTTVAR - 1] = m; else dst->metrics[RTAX_RTTVAR-1] -= - (dst_metric(dst, RTAX_RTTVAR) - m)>>2; + (dst->metrics[RTAX_RTTVAR-1] - m)>>2; } if (tp->snd_ssthresh >= 0xFFFF) { @@ -789,21 +788,21 @@ void tcp_update_metrics(struct sock *sk) dst->metrics[RTAX_SSTHRESH-1] = max(tp->snd_cwnd >> 1, tp->snd_ssthresh); if (!dst_metric_locked(dst, RTAX_CWND)) - dst->metrics[RTAX_CWND-1] = (dst_metric(dst, RTAX_CWND) + tp->snd_cwnd) >> 1; + dst->metrics[RTAX_CWND-1] = (dst->metrics[RTAX_CWND-1] + tp->snd_cwnd) >> 1; } else { /* Else slow start did not finish, cwnd is non-sense, ssthresh may be also invalid. */ if (!dst_metric_locked(dst, RTAX_CWND)) - dst->metrics[RTAX_CWND-1] = (dst_metric(dst, RTAX_CWND) + tp->snd_ssthresh) >> 1; - if (dst_metric(dst, RTAX_SSTHRESH) && + dst->metrics[RTAX_CWND-1] = (dst->metrics[RTAX_CWND-1] + tp->snd_ssthresh) >> 1; + if (dst->metrics[RTAX_SSTHRESH-1] && !dst_metric_locked(dst, RTAX_SSTHRESH) && - tp->snd_ssthresh > dst_metric(dst, RTAX_SSTHRESH)) + tp->snd_ssthresh > dst->metrics[RTAX_SSTHRESH-1]) dst->metrics[RTAX_SSTHRESH-1] = tp->snd_ssthresh; } if (!dst_metric_locked(dst, RTAX_REORDERING)) { - if (dst_metric(dst, RTAX_REORDERING) < tp->reordering && + if (dst->metrics[RTAX_REORDERING-1] < tp->reordering && tp->reordering != sysctl_tcp_reordering) dst->metrics[RTAX_REORDERING-1] = tp->reordering; } diff --git a/trunk/net/ipv6/route.c b/trunk/net/ipv6/route.c index 12bba0880345..a493ad9b8914 100644 --- a/trunk/net/ipv6/route.c +++ b/trunk/net/ipv6/route.c @@ -1243,11 +1243,11 @@ int ip6_route_add(struct fib6_config *cfg) } } - if (dst_metric(&rt->u.dst, RTAX_HOPLIMIT) == 0) + if (rt->u.dst.metrics[RTAX_HOPLIMIT-1] == 0) rt->u.dst.metrics[RTAX_HOPLIMIT-1] = -1; - if (!dst_metric(&rt->u.dst, RTAX_MTU)) + if (!rt->u.dst.metrics[RTAX_MTU-1]) rt->u.dst.metrics[RTAX_MTU-1] = ipv6_get_mtu(dev); - if (!dst_metric(&rt->u.dst, RTAX_ADVMSS)) + if (!rt->u.dst.metrics[RTAX_ADVMSS-1]) rt->u.dst.metrics[RTAX_ADVMSS-1] = ipv6_advmss(net, dst_mtu(&rt->u.dst)); rt->u.dst.dev = dev; rt->rt6i_idev = idev; diff --git a/trunk/net/mac80211/main.c b/trunk/net/mac80211/main.c index 915afadb0602..9ad4e3631b6b 100644 --- a/trunk/net/mac80211/main.c +++ b/trunk/net/mac80211/main.c @@ -1766,7 +1766,6 @@ int ieee80211_register_hw(struct ieee80211_hw *hw) fail_rate: ieee80211_debugfs_remove_netdev(IEEE80211_DEV_TO_SUB_IF(local->mdev)); unregister_netdevice(local->mdev); - local->mdev = NULL; fail_dev: rtnl_unlock(); sta_info_stop(local); @@ -1774,10 +1773,8 @@ int ieee80211_register_hw(struct ieee80211_hw *hw) debugfs_hw_del(local); destroy_workqueue(local->hw.workqueue); fail_workqueue: - if (local->mdev != NULL) { - ieee80211_if_free(local->mdev); - local->mdev = NULL; - } + ieee80211_if_free(local->mdev); + local->mdev = NULL; fail_mdev_alloc: wiphy_unregister(local->hw.wiphy); return result; diff --git a/trunk/net/sched/act_simple.c b/trunk/net/sched/act_simple.c index 1d421d059caf..64b2d136c78e 100644 --- a/trunk/net/sched/act_simple.c +++ b/trunk/net/sched/act_simple.c @@ -6,7 +6,7 @@ * as published by the Free Software Foundation; either version * 2 of the License, or (at your option) any later version. * - * Authors: Jamal Hadi Salim (2005-8) + * Authors: Jamal Hadi Salim (2005) * */ @@ -34,7 +34,6 @@ static struct tcf_hashinfo simp_hash_info = { .lock = &simp_lock, }; -#define SIMP_MAX_DATA 32 static int tcf_simp(struct sk_buff *skb, struct tc_action *a, struct tcf_result *res) { struct tcf_defact *d = a->priv; @@ -70,28 +69,23 @@ static int tcf_simp_release(struct tcf_defact *d, int bind) return ret; } -static int alloc_defdata(struct tcf_defact *d, char *defdata) +static int alloc_defdata(struct tcf_defact *d, u32 datalen, void *defdata) { - d->tcfd_defdata = kstrndup(defdata, SIMP_MAX_DATA, GFP_KERNEL); + d->tcfd_defdata = kmemdup(defdata, datalen, GFP_KERNEL); if (unlikely(!d->tcfd_defdata)) return -ENOMEM; - + d->tcfd_datalen = datalen; return 0; } -static void reset_policy(struct tcf_defact *d, char *defdata, - struct tc_defact *p) +static int realloc_defdata(struct tcf_defact *d, u32 datalen, void *defdata) { - spin_lock_bh(&d->tcf_lock); - d->tcf_action = p->action; - memset(d->tcfd_defdata, 0, SIMP_MAX_DATA); - strlcpy(d->tcfd_defdata, defdata, SIMP_MAX_DATA); - spin_unlock_bh(&d->tcf_lock); + kfree(d->tcfd_defdata); + return alloc_defdata(d, datalen, defdata); } static const struct nla_policy simple_policy[TCA_DEF_MAX + 1] = { [TCA_DEF_PARMS] = { .len = sizeof(struct tc_defact) }, - [TCA_DEF_DATA] = { .type = NLA_STRING, .len = SIMP_MAX_DATA }, }; static int tcf_simp_init(struct nlattr *nla, struct nlattr *est, @@ -101,24 +95,28 @@ static int tcf_simp_init(struct nlattr *nla, struct nlattr *est, struct tc_defact *parm; struct tcf_defact *d; struct tcf_common *pc; - char *defdata; + void *defdata; + u32 datalen = 0; int ret = 0, err; if (nla == NULL) return -EINVAL; - err = nla_parse_nested(tb, TCA_DEF_MAX, nla, simple_policy); + err = nla_parse_nested(tb, TCA_DEF_MAX, nla, NULL); if (err < 0) return err; if (tb[TCA_DEF_PARMS] == NULL) return -EINVAL; - if (tb[TCA_DEF_DATA] == NULL) - return -EINVAL; - parm = nla_data(tb[TCA_DEF_PARMS]); defdata = nla_data(tb[TCA_DEF_DATA]); + if (defdata == NULL) + return -EINVAL; + + datalen = nla_len(tb[TCA_DEF_DATA]); + if (datalen == 0) + return -EINVAL; pc = tcf_hash_check(parm->index, a, bind, &simp_hash_info); if (!pc) { @@ -128,12 +126,11 @@ static int tcf_simp_init(struct nlattr *nla, struct nlattr *est, return -ENOMEM; d = to_defact(pc); - ret = alloc_defdata(d, defdata); + ret = alloc_defdata(d, datalen, defdata); if (ret < 0) { kfree(pc); return ret; } - d->tcf_action = parm->action; ret = ACT_P_CREATED; } else { d = to_defact(pc); @@ -141,9 +138,13 @@ static int tcf_simp_init(struct nlattr *nla, struct nlattr *est, tcf_simp_release(d, bind); return -EEXIST; } - reset_policy(d, defdata, parm); + realloc_defdata(d, datalen, defdata); } + spin_lock_bh(&d->tcf_lock); + d->tcf_action = parm->action; + spin_unlock_bh(&d->tcf_lock); + if (ret == ACT_P_CREATED) tcf_hash_insert(pc, &simp_hash_info); return ret; @@ -171,7 +172,7 @@ static inline int tcf_simp_dump(struct sk_buff *skb, struct tc_action *a, opt.bindcnt = d->tcf_bindcnt - bind; opt.action = d->tcf_action; NLA_PUT(skb, TCA_DEF_PARMS, sizeof(opt), &opt); - NLA_PUT_STRING(skb, TCA_DEF_DATA, d->tcfd_defdata); + NLA_PUT(skb, TCA_DEF_DATA, d->tcfd_datalen, d->tcfd_defdata); t.install = jiffies_to_clock_t(jiffies - d->tcf_tm.install); t.lastuse = jiffies_to_clock_t(jiffies - d->tcf_tm.lastuse); t.expires = jiffies_to_clock_t(d->tcf_tm.expires); diff --git a/trunk/net/sched/sch_htb.c b/trunk/net/sched/sch_htb.c index 5bc1ed490180..66148cc4759e 100644 --- a/trunk/net/sched/sch_htb.c +++ b/trunk/net/sched/sch_htb.c @@ -1197,16 +1197,12 @@ static inline int htb_parent_last_child(struct htb_class *cl) return 1; } -static void htb_parent_to_leaf(struct htb_sched *q, struct htb_class *cl, - struct Qdisc *new_q) +static void htb_parent_to_leaf(struct htb_class *cl, struct Qdisc *new_q) { struct htb_class *parent = cl->parent; BUG_TRAP(!cl->level && cl->un.leaf.q && !cl->prio_activity); - if (parent->cmode != HTB_CAN_SEND) - htb_safe_rb_erase(&parent->pq_node, q->wait_pq + parent->level); - parent->level = 0; memset(&parent->un.inner, 0, sizeof(parent->un.inner)); INIT_LIST_HEAD(&parent->un.leaf.drop_list); @@ -1304,7 +1300,7 @@ static int htb_delete(struct Qdisc *sch, unsigned long arg) htb_deactivate(q, cl); if (last_child) - htb_parent_to_leaf(q, cl, new_q); + htb_parent_to_leaf(cl, new_q); if (--cl->refcnt == 0) htb_destroy_class(sch, cl);