Commit 1f3f424a authored by Ingo Molnar's avatar Ingo Molnar

Merge branch 'linus' into cpus4096

parents c8cae544 1bda7128
...@@ -24,7 +24,7 @@ real bad - it changes the behaviour of all unaligned instructions in user ...@@ -24,7 +24,7 @@ real bad - it changes the behaviour of all unaligned instructions in user
space, and might cause programs to fail unexpectedly. space, and might cause programs to fail unexpectedly.
To change the alignment trap behavior, simply echo a number into To change the alignment trap behavior, simply echo a number into
/proc/sys/debug/alignment. The number is made up from various bits: /proc/cpu/alignment. The number is made up from various bits:
bit behavior when set bit behavior when set
--- ----------------- --- -----------------
......
...@@ -1527,10 +1527,10 @@ W: http://ebtables.sourceforge.net/ ...@@ -1527,10 +1527,10 @@ W: http://ebtables.sourceforge.net/
S: Maintained S: Maintained
ECRYPT FILE SYSTEM ECRYPT FILE SYSTEM
P: Mike Halcrow, Phillip Hellewell P: Tyler Hicks, Dustin Kirkland
M: mhalcrow@us.ibm.com, phillip@hellewell.homeip.net M: tyhicks@linux.vnet.ibm.com, kirkland@canonical.com
L: ecryptfs-devel@lists.sourceforge.net L: ecryptfs-devel@lists.launchpad.net
W: http://ecryptfs.sourceforge.net/ W: https://launchpad.net/ecryptfs
S: Supported S: Supported
EDAC-CORE EDAC-CORE
......
...@@ -630,7 +630,7 @@ __sa1111_probe(struct device *me, struct resource *mem, int irq) ...@@ -630,7 +630,7 @@ __sa1111_probe(struct device *me, struct resource *mem, int irq)
return -ENOMEM; return -ENOMEM;
sachip->clk = clk_get(me, "SA1111_CLK"); sachip->clk = clk_get(me, "SA1111_CLK");
if (!sachip->clk) { if (IS_ERR(sachip->clk)) {
ret = PTR_ERR(sachip->clk); ret = PTR_ERR(sachip->clk);
goto err_free; goto err_free;
} }
......
...@@ -115,6 +115,8 @@ EXPORT_SYMBOL(__strnlen_user); ...@@ -115,6 +115,8 @@ EXPORT_SYMBOL(__strnlen_user);
EXPORT_SYMBOL(__strncpy_from_user); EXPORT_SYMBOL(__strncpy_from_user);
#ifdef CONFIG_MMU #ifdef CONFIG_MMU
EXPORT_SYMBOL(copy_page);
EXPORT_SYMBOL(__copy_from_user); EXPORT_SYMBOL(__copy_from_user);
EXPORT_SYMBOL(__copy_to_user); EXPORT_SYMBOL(__copy_to_user);
EXPORT_SYMBOL(__clear_user); EXPORT_SYMBOL(__clear_user);
...@@ -181,8 +183,6 @@ EXPORT_SYMBOL(_find_first_bit_be); ...@@ -181,8 +183,6 @@ EXPORT_SYMBOL(_find_first_bit_be);
EXPORT_SYMBOL(_find_next_bit_be); EXPORT_SYMBOL(_find_next_bit_be);
#endif #endif
EXPORT_SYMBOL(copy_page);
#ifdef CONFIG_FUNCTION_TRACER #ifdef CONFIG_FUNCTION_TRACER
EXPORT_SYMBOL(mcount); EXPORT_SYMBOL(mcount);
#endif #endif
...@@ -18,6 +18,7 @@ ...@@ -18,6 +18,7 @@
#include <linux/personality.h> #include <linux/personality.h>
#include <linux/kallsyms.h> #include <linux/kallsyms.h>
#include <linux/delay.h> #include <linux/delay.h>
#include <linux/hardirq.h>
#include <linux/init.h> #include <linux/init.h>
#include <linux/uaccess.h> #include <linux/uaccess.h>
......
...@@ -12,9 +12,8 @@ extern void clear_reset_status(unsigned int mask); ...@@ -12,9 +12,8 @@ extern void clear_reset_status(unsigned int mask);
/** /**
* init_gpio_reset() - register GPIO as reset generator * init_gpio_reset() - register GPIO as reset generator
* * @gpio: gpio nr
* @gpio - gpio nr * @output: set gpio as out/low instead of input during normal work
* @output - set gpio as out/low instead of input during normal work
*/ */
extern int init_gpio_reset(int gpio, int output); extern int init_gpio_reset(int gpio, int output);
......
...@@ -11,6 +11,7 @@ ...@@ -11,6 +11,7 @@
#include <linux/module.h> #include <linux/module.h>
#include <linux/signal.h> #include <linux/signal.h>
#include <linux/mm.h> #include <linux/mm.h>
#include <linux/hardirq.h>
#include <linux/init.h> #include <linux/init.h>
#include <linux/kprobes.h> #include <linux/kprobes.h>
#include <linux/uaccess.h> #include <linux/uaccess.h>
......
...@@ -4,6 +4,7 @@ menu "HP Simulator drivers" ...@@ -4,6 +4,7 @@ menu "HP Simulator drivers"
config HP_SIMETH config HP_SIMETH
bool "Simulated Ethernet " bool "Simulated Ethernet "
depends on NET
config HP_SIMSERIAL config HP_SIMSERIAL
bool "Simulated serial driver support" bool "Simulated serial driver support"
......
...@@ -479,6 +479,8 @@ _GLOBAL(_tlbil_pid) ...@@ -479,6 +479,8 @@ _GLOBAL(_tlbil_pid)
* (no broadcast) * (no broadcast)
*/ */
_GLOBAL(_tlbil_va) _GLOBAL(_tlbil_va)
mfmsr r10
wrteei 0
slwi r4,r4,16 slwi r4,r4,16
mtspr SPRN_MAS6,r4 /* assume AS=0 for now */ mtspr SPRN_MAS6,r4 /* assume AS=0 for now */
tlbsx 0,r3 tlbsx 0,r3
...@@ -490,6 +492,7 @@ _GLOBAL(_tlbil_va) ...@@ -490,6 +492,7 @@ _GLOBAL(_tlbil_va)
tlbwe tlbwe
msync msync
isync isync
wrtee r10
blr blr
#endif /* CONFIG_FSL_BOOKE */ #endif /* CONFIG_FSL_BOOKE */
......
...@@ -507,6 +507,9 @@ unsigned long hugetlb_get_unmapped_area(struct file *file, unsigned long addr, ...@@ -507,6 +507,9 @@ unsigned long hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
{ {
struct hstate *hstate = hstate_file(file); struct hstate *hstate = hstate_file(file);
int mmu_psize = shift_to_mmu_psize(huge_page_shift(hstate)); int mmu_psize = shift_to_mmu_psize(huge_page_shift(hstate));
if (!mmu_huge_psizes[mmu_psize])
return -EINVAL;
return slice_get_unmapped_area(addr, len, flags, mmu_psize, 1, 0); return slice_get_unmapped_area(addr, len, flags, mmu_psize, 1, 0);
} }
......
...@@ -901,10 +901,17 @@ static void mark_reserved_regions_for_nid(int nid) ...@@ -901,10 +901,17 @@ static void mark_reserved_regions_for_nid(int nid)
if (end_pfn > node_ar.end_pfn) if (end_pfn > node_ar.end_pfn)
reserve_size = (node_ar.end_pfn << PAGE_SHIFT) reserve_size = (node_ar.end_pfn << PAGE_SHIFT)
- (start_pfn << PAGE_SHIFT); - (start_pfn << PAGE_SHIFT);
dbg("reserve_bootmem %lx %lx nid=%d\n", physbase, /*
reserve_size, node_ar.nid); * Only worry about *this* node, others may not
reserve_bootmem_node(NODE_DATA(node_ar.nid), physbase, * yet have valid NODE_DATA().
reserve_size, BOOTMEM_DEFAULT); */
if (node_ar.nid == nid) {
dbg("reserve_bootmem %lx %lx nid=%d\n",
physbase, reserve_size, node_ar.nid);
reserve_bootmem_node(NODE_DATA(node_ar.nid),
physbase, reserve_size,
BOOTMEM_DEFAULT);
}
/* /*
* if reserved region is contained in the active region * if reserved region is contained in the active region
* then done. * then done.
...@@ -929,7 +936,6 @@ static void mark_reserved_regions_for_nid(int nid) ...@@ -929,7 +936,6 @@ static void mark_reserved_regions_for_nid(int nid)
void __init do_init_bootmem(void) void __init do_init_bootmem(void)
{ {
int nid; int nid;
unsigned int i;
min_low_pfn = 0; min_low_pfn = 0;
max_low_pfn = lmb_end_of_DRAM() >> PAGE_SHIFT; max_low_pfn = lmb_end_of_DRAM() >> PAGE_SHIFT;
......
...@@ -413,6 +413,9 @@ static int axon_msi_probe(struct of_device *device, ...@@ -413,6 +413,9 @@ static int axon_msi_probe(struct of_device *device,
MSIC_CTRL_IRQ_ENABLE | MSIC_CTRL_ENABLE | MSIC_CTRL_IRQ_ENABLE | MSIC_CTRL_ENABLE |
MSIC_CTRL_FIFO_SIZE); MSIC_CTRL_FIFO_SIZE);
msic->read_offset = dcr_read(msic->dcr_host, MSIC_WRITE_OFFSET_REG)
& MSIC_FIFO_SIZE_MASK;
device->dev.platform_data = msic; device->dev.platform_data = msic;
ppc_md.setup_msi_irqs = axon_msi_setup_msi_irqs; ppc_md.setup_msi_irqs = axon_msi_setup_msi_irqs;
......
...@@ -55,6 +55,8 @@ config GENERIC_HARDIRQS ...@@ -55,6 +55,8 @@ config GENERIC_HARDIRQS
config GENERIC_HARDIRQS_NO__DO_IRQ config GENERIC_HARDIRQS_NO__DO_IRQ
def_bool y def_bool y
depends on SUPERH32 && (!SH_DREAMCAST && !SH_SH4202_MICRODEV && \
!SH_7751_SYSTEMH && !HD64461)
config GENERIC_IRQ_PROBE config GENERIC_IRQ_PROBE
def_bool y def_bool y
......
...@@ -223,9 +223,15 @@ struct pci_header { ...@@ -223,9 +223,15 @@ struct pci_header {
} __attribute__((packed)); } __attribute__((packed));
/* Function prototypes for bootstrapping */ /* Function prototypes for bootstrapping */
#ifdef CONFIG_VMI
extern void vmi_init(void); extern void vmi_init(void);
extern void vmi_activate(void);
extern void vmi_bringup(void); extern void vmi_bringup(void);
extern void vmi_apply_boot_page_allocations(void); #else
static inline void vmi_init(void) {}
static inline void vmi_activate(void) {}
static inline void vmi_bringup(void) {}
#endif
/* State needed to start an application processor in an SMP system. */ /* State needed to start an application processor in an SMP system. */
struct vmi_ap_state { struct vmi_ap_state {
......
...@@ -807,6 +807,9 @@ void __init setup_arch(char **cmdline_p) ...@@ -807,6 +807,9 @@ void __init setup_arch(char **cmdline_p)
printk(KERN_INFO "Command line: %s\n", boot_command_line); printk(KERN_INFO "Command line: %s\n", boot_command_line);
#endif #endif
/* VMI may relocate the fixmap; do this before touching ioremap area */
vmi_init();
early_cpu_init(); early_cpu_init();
early_ioremap_init(); early_ioremap_init();
...@@ -893,13 +896,8 @@ void __init setup_arch(char **cmdline_p) ...@@ -893,13 +896,8 @@ void __init setup_arch(char **cmdline_p)
check_efer(); check_efer();
#endif #endif
#if defined(CONFIG_VMI) && defined(CONFIG_X86_32) /* Must be before kernel pagetables are setup */
/* vmi_activate();
* Must be before kernel pagetables are setup
* or fixmap area is touched.
*/
vmi_init();
#endif
/* after early param, so could get panic from serial */ /* after early param, so could get panic from serial */
reserve_early_setup_data(); reserve_early_setup_data();
......
...@@ -289,9 +289,7 @@ static void __cpuinit start_secondary(void *unused) ...@@ -289,9 +289,7 @@ static void __cpuinit start_secondary(void *unused)
* fragile that we want to limit the things done here to the * fragile that we want to limit the things done here to the
* most necessary things. * most necessary things.
*/ */
#ifdef CONFIG_VMI
vmi_bringup(); vmi_bringup();
#endif
cpu_init(); cpu_init();
preempt_disable(); preempt_disable();
smp_callin(); smp_callin();
......
...@@ -960,8 +960,6 @@ static inline int __init activate_vmi(void) ...@@ -960,8 +960,6 @@ static inline int __init activate_vmi(void)
void __init vmi_init(void) void __init vmi_init(void)
{ {
unsigned long flags;
if (!vmi_rom) if (!vmi_rom)
probe_vmi_rom(); probe_vmi_rom();
else else
...@@ -973,13 +971,21 @@ void __init vmi_init(void) ...@@ -973,13 +971,21 @@ void __init vmi_init(void)
reserve_top_address(-vmi_rom->virtual_top); reserve_top_address(-vmi_rom->virtual_top);
local_irq_save(flags);
activate_vmi();
#ifdef CONFIG_X86_IO_APIC #ifdef CONFIG_X86_IO_APIC
/* This is virtual hardware; timer routing is wired correctly */ /* This is virtual hardware; timer routing is wired correctly */
no_timer_check = 1; no_timer_check = 1;
#endif #endif
}
void vmi_activate(void)
{
unsigned long flags;
if (!vmi_rom)
return;
local_irq_save(flags);
activate_vmi();
local_irq_restore(flags & X86_EFLAGS_IF); local_irq_restore(flags & X86_EFLAGS_IF);
} }
......
...@@ -824,12 +824,12 @@ static int __init toshiba_acpi_init(void) ...@@ -824,12 +824,12 @@ static int __init toshiba_acpi_init(void)
toshiba_acpi_exit(); toshiba_acpi_exit();
return -ENOMEM; return -ENOMEM;
} }
}
/* Register input device for kill switch */ /* Register input device for kill switch */
toshiba_acpi.poll_dev = input_allocate_polled_device(); toshiba_acpi.poll_dev = input_allocate_polled_device();
if (!toshiba_acpi.poll_dev) { if (!toshiba_acpi.poll_dev) {
printk(MY_ERR "unable to allocate kill-switch input device\n"); printk(MY_ERR
"unable to allocate kill-switch input device\n");
toshiba_acpi_exit(); toshiba_acpi_exit();
return -ENOMEM; return -ENOMEM;
} }
...@@ -839,18 +839,22 @@ static int __init toshiba_acpi_init(void) ...@@ -839,18 +839,22 @@ static int __init toshiba_acpi_init(void)
toshiba_acpi.poll_dev->input->name = toshiba_acpi.rfk_name; toshiba_acpi.poll_dev->input->name = toshiba_acpi.rfk_name;
toshiba_acpi.poll_dev->input->id.bustype = BUS_HOST; toshiba_acpi.poll_dev->input->id.bustype = BUS_HOST;
toshiba_acpi.poll_dev->input->id.vendor = 0x0930; /* Toshiba USB ID */ /* Toshiba USB ID */
toshiba_acpi.poll_dev->input->id.vendor = 0x0930;
set_bit(EV_SW, toshiba_acpi.poll_dev->input->evbit); set_bit(EV_SW, toshiba_acpi.poll_dev->input->evbit);
set_bit(SW_RFKILL_ALL, toshiba_acpi.poll_dev->input->swbit); set_bit(SW_RFKILL_ALL, toshiba_acpi.poll_dev->input->swbit);
input_report_switch(toshiba_acpi.poll_dev->input, SW_RFKILL_ALL, TRUE); input_report_switch(toshiba_acpi.poll_dev->input,
SW_RFKILL_ALL, TRUE);
input_sync(toshiba_acpi.poll_dev->input); input_sync(toshiba_acpi.poll_dev->input);
ret = input_register_polled_device(toshiba_acpi.poll_dev); ret = input_register_polled_device(toshiba_acpi.poll_dev);
if (ret) { if (ret) {
printk(MY_ERR "unable to register kill-switch input device\n"); printk(MY_ERR
"unable to register kill-switch input device\n");
toshiba_acpi_exit(); toshiba_acpi_exit();
return ret; return ret;
} }
}
return 0; return 0;
} }
......
...@@ -4050,17 +4050,70 @@ static const struct ata_blacklist_entry ata_device_blacklist [] = { ...@@ -4050,17 +4050,70 @@ static const struct ata_blacklist_entry ata_device_blacklist [] = {
{ "ST3160023AS", "3.42", ATA_HORKAGE_NONCQ }, { "ST3160023AS", "3.42", ATA_HORKAGE_NONCQ },
/* Seagate NCQ + FLUSH CACHE firmware bug */ /* Seagate NCQ + FLUSH CACHE firmware bug */
{ "ST31500341AS", "9JU138", ATA_HORKAGE_NONCQ | { "ST31500341AS", "SD15", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN }, ATA_HORKAGE_FIRMWARE_WARN },
{ "ST31000333AS", "9FZ136", ATA_HORKAGE_NONCQ | { "ST31500341AS", "SD16", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN }, ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3640623AS", "9FZ164", ATA_HORKAGE_NONCQ | { "ST31500341AS", "SD17", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN }, ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3640323AS", "9FZ134", ATA_HORKAGE_NONCQ | { "ST31500341AS", "SD18", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN }, ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3320813AS", "9FZ182", ATA_HORKAGE_NONCQ | { "ST31500341AS", "SD19", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN }, ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3320613AS", "9FZ162", ATA_HORKAGE_NONCQ |
{ "ST31000333AS", "SD15", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST31000333AS", "SD16", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST31000333AS", "SD17", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST31000333AS", "SD18", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST31000333AS", "SD19", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3640623AS", "SD15", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3640623AS", "SD16", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3640623AS", "SD17", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3640623AS", "SD18", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3640623AS", "SD19", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3640323AS", "SD15", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3640323AS", "SD16", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3640323AS", "SD17", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3640323AS", "SD18", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3640323AS", "SD19", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3320813AS", "SD15", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3320813AS", "SD16", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3320813AS", "SD17", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3320813AS", "SD18", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3320813AS", "SD19", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3320613AS", "SD15", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3320613AS", "SD16", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3320613AS", "SD17", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3320613AS", "SD18", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN },
{ "ST3320613AS", "SD19", ATA_HORKAGE_NONCQ |
ATA_HORKAGE_FIRMWARE_WARN }, ATA_HORKAGE_FIRMWARE_WARN },
/* Blacklist entries taken from Silicon Image 3124/3132 /* Blacklist entries taken from Silicon Image 3124/3132
......
...@@ -183,7 +183,9 @@ static unsigned long hpt366_filter(struct ata_device *adev, unsigned long mask) ...@@ -183,7 +183,9 @@ static unsigned long hpt366_filter(struct ata_device *adev, unsigned long mask)
mask &= ~(0xF8 << ATA_SHIFT_UDMA); mask &= ~(0xF8 << ATA_SHIFT_UDMA);
if (hpt_dma_blacklisted(adev, "UDMA4", bad_ata66_4)) if (hpt_dma_blacklisted(adev, "UDMA4", bad_ata66_4))
mask &= ~(0xF0 << ATA_SHIFT_UDMA); mask &= ~(0xF0 << ATA_SHIFT_UDMA);
} } else if (adev->class == ATA_DEV_ATAPI)
mask &= ~(ATA_MASK_MWDMA | ATA_MASK_UDMA);
return ata_bmdma_mode_filter(adev, mask); return ata_bmdma_mode_filter(adev, mask);
} }
...@@ -211,11 +213,15 @@ static u32 hpt36x_find_mode(struct ata_port *ap, int speed) ...@@ -211,11 +213,15 @@ static u32 hpt36x_find_mode(struct ata_port *ap, int speed)
static int hpt36x_cable_detect(struct ata_port *ap) static int hpt36x_cable_detect(struct ata_port *ap)
{ {
u8 ata66;
struct pci_dev *pdev = to_pci_dev(ap->host->dev); struct pci_dev *pdev = to_pci_dev(ap->host->dev);
u8 ata66;
/*
* Each channel of pata_hpt366 occupies separate PCI function
* as the primary channel and bit1 indicates the cable type.
*/
pci_read_config_byte(pdev, 0x5A, &ata66); pci_read_config_byte(pdev, 0x5A, &ata66);
if (ata66 & (1 << ap->port_no)) if (ata66 & 2)
return ATA_CBL_PATA40; return ATA_CBL_PATA40;
return ATA_CBL_PATA80; return ATA_CBL_PATA80;
} }
......
...@@ -115,8 +115,14 @@ static int nodemgr_bus_read(struct csr1212_csr *csr, u64 addr, u16 length, ...@@ -115,8 +115,14 @@ static int nodemgr_bus_read(struct csr1212_csr *csr, u64 addr, u16 length,
return error; return error;
} }
#define OUI_FREECOM_TECHNOLOGIES_GMBH 0x0001db
static int nodemgr_get_max_rom(quadlet_t *bus_info_data, void *__ci) static int nodemgr_get_max_rom(quadlet_t *bus_info_data, void *__ci)
{ {
/* Freecom FireWire Hard Drive firmware bug */
if (be32_to_cpu(bus_info_data[3]) >> 8 == OUI_FREECOM_TECHNOLOGIES_GMBH)
return 0;
return (be32_to_cpu(bus_info_data[2]) >> 8) & 0x3; return (be32_to_cpu(bus_info_data[2]) >> 8) & 0x3;
} }
......
...@@ -1893,12 +1893,17 @@ static s32 e1000_reset_hw_ich8lan(struct e1000_hw *hw) ...@@ -1893,12 +1893,17 @@ static s32 e1000_reset_hw_ich8lan(struct e1000_hw *hw)
ctrl |= E1000_CTRL_PHY_RST; ctrl |= E1000_CTRL_PHY_RST;
} }
ret_val = e1000_acquire_swflag_ich8lan(hw); ret_val = e1000_acquire_swflag_ich8lan(hw);
/* Whether or not the swflag was acquired, we need to reset the part */
hw_dbg(hw, "Issuing a global reset to ich8lan"); hw_dbg(hw, "Issuing a global reset to ich8lan");
ew32(CTRL, (ctrl | E1000_CTRL_RST)); ew32(CTRL, (ctrl | E1000_CTRL_RST));
msleep(20); msleep(20);
/* release the swflag because it is not reset by hardware reset */ if (!ret_val) {
/* release the swflag because it is not reset by
* hardware reset
*/
e1000_release_swflag_ich8lan(hw); e1000_release_swflag_ich8lan(hw);
}
ret_val = e1000e_get_auto_rd_done(hw); ret_val = e1000e_get_auto_rd_done(hw);
if (ret_val) { if (ret_val) {
......
...@@ -1142,6 +1142,70 @@ static int gem_start_xmit(struct sk_buff *skb, struct net_device *dev) ...@@ -1142,6 +1142,70 @@ static int gem_start_xmit(struct sk_buff *skb, struct net_device *dev)
return NETDEV_TX_OK; return NETDEV_TX_OK;
} }
static void gem_pcs_reset(struct gem *gp)
{
int limit;
u32 val;
/* Reset PCS unit. */
val = readl(gp->regs + PCS_MIICTRL);
val |= PCS_MIICTRL_RST;
writel(val, gp->regs + PCS_MIICTRL);
limit = 32;
while (readl(gp->regs + PCS_MIICTRL) & PCS_MIICTRL_RST) {
udelay(100);
if (limit-- <= 0)
break;
}
if (limit <= 0)
printk(KERN_WARNING "%s: PCS reset bit would not clear.\n",
gp->dev->name);
}
static void gem_pcs_reinit_adv(struct gem *gp)
{
u32 val;
/* Make sure PCS is disabled while changing advertisement
* configuration.
*/
val = readl(gp->regs + PCS_CFG);
val &= ~(PCS_CFG_ENABLE | PCS_CFG_TO);
writel(val, gp->regs + PCS_CFG);
/* Advertise all capabilities except assymetric
* pause.
*/
val = readl(gp->regs + PCS_MIIADV);
val |= (PCS_MIIADV_FD | PCS_MIIADV_HD |
PCS_MIIADV_SP | PCS_MIIADV_AP);
writel(val, gp->regs + PCS_MIIADV);
/* Enable and restart auto-negotiation, disable wrapback/loopback,
* and re-enable PCS.
*/
val = readl(gp->regs + PCS_MIICTRL);
val |= (PCS_MIICTRL_RAN | PCS_MIICTRL_ANE);
val &= ~PCS_MIICTRL_WB;
writel(val, gp->regs + PCS_MIICTRL);
val = readl(gp->regs + PCS_CFG);
val |= PCS_CFG_ENABLE;
writel(val, gp->regs + PCS_CFG);
/* Make sure serialink loopback is off. The meaning
* of this bit is logically inverted based upon whether
* you are in Serialink or SERDES mode.
*/
val = readl(gp->regs + PCS_SCTRL);
if (gp->phy_type == phy_serialink)
val &= ~PCS_SCTRL_LOOP;
else
val |= PCS_SCTRL_LOOP;
writel(val, gp->regs + PCS_SCTRL);
}
#define STOP_TRIES 32 #define STOP_TRIES 32
/* Must be invoked under gp->lock and gp->tx_lock. */ /* Must be invoked under gp->lock and gp->tx_lock. */
...@@ -1168,6 +1232,9 @@ static void gem_reset(struct gem *gp) ...@@ -1168,6 +1232,9 @@ static void gem_reset(struct gem *gp)
if (limit <= 0) if (limit <= 0)
printk(KERN_ERR "%s: SW reset is ghetto.\n", gp->dev->name); printk(KERN_ERR "%s: SW reset is ghetto.\n", gp->dev->name);
if (gp->phy_type == phy_serialink || gp->phy_type == phy_serdes)
gem_pcs_reinit_adv(gp);
} }
/* Must be invoked under gp->lock and gp->tx_lock. */ /* Must be invoked under gp->lock and gp->tx_lock. */
...@@ -1324,7 +1391,7 @@ static int gem_set_link_modes(struct gem *gp) ...@@ -1324,7 +1391,7 @@ static int gem_set_link_modes(struct gem *gp)
gp->phy_type == phy_serdes) { gp->phy_type == phy_serdes) {
u32 pcs_lpa = readl(gp->regs + PCS_MIILP); u32 pcs_lpa = readl(gp->regs + PCS_MIILP);
if (pcs_lpa & PCS_MIIADV_FD) if ((pcs_lpa & PCS_MIIADV_FD) || gp->phy_type == phy_serdes)
full_duplex = 1; full_duplex = 1;
speed = SPEED_1000; speed = SPEED_1000;
} }
...@@ -1488,6 +1555,9 @@ static void gem_link_timer(unsigned long data) ...@@ -1488,6 +1555,9 @@ static void gem_link_timer(unsigned long data)
val = readl(gp->regs + PCS_MIISTAT); val = readl(gp->regs + PCS_MIISTAT);
if ((val & PCS_MIISTAT_LS) != 0) { if ((val & PCS_MIISTAT_LS) != 0) {
if (gp->lstate == link_up)
goto restart;
gp->lstate = link_up; gp->lstate = link_up;
netif_carrier_on(gp->dev); netif_carrier_on(gp->dev);
(void)gem_set_link_modes(gp); (void)gem_set_link_modes(gp);
...@@ -1708,61 +1778,8 @@ static void gem_init_phy(struct gem *gp) ...@@ -1708,61 +1778,8 @@ static void gem_init_phy(struct gem *gp)
if (gp->phy_mii.def && gp->phy_mii.def->ops->init) if (gp->phy_mii.def && gp->phy_mii.def->ops->init)
gp->phy_mii.def->ops->init(&gp->phy_mii); gp->phy_mii.def->ops->init(&gp->phy_mii);
} else { } else {
u32 val; gem_pcs_reset(gp);
int limit; gem_pcs_reinit_adv(gp);
/* Reset PCS unit. */
val = readl(gp->regs + PCS_MIICTRL);
val |= PCS_MIICTRL_RST;
writel(val, gp->regs + PCS_MIICTRL);
limit = 32;
while (readl(gp->regs + PCS_MIICTRL) & PCS_MIICTRL_RST) {
udelay(100);
if (limit-- <= 0)
break;
}
if (limit <= 0)
printk(KERN_WARNING "%s: PCS reset bit would not clear.\n",
gp->dev->name);
/* Make sure PCS is disabled while changing advertisement
* configuration.
*/
val = readl(gp->regs + PCS_CFG);
val &= ~(PCS_CFG_ENABLE | PCS_CFG_TO);
writel(val, gp->regs + PCS_CFG);
/* Advertise all capabilities except assymetric
* pause.
*/
val = readl(gp->regs + PCS_MIIADV);
val |= (PCS_MIIADV_FD | PCS_MIIADV_HD |
PCS_MIIADV_SP | PCS_MIIADV_AP);
writel(val, gp->regs + PCS_MIIADV);
/* Enable and restart auto-negotiation, disable wrapback/loopback,
* and re-enable PCS.
*/
val = readl(gp->regs + PCS_MIICTRL);
val |= (PCS_MIICTRL_RAN | PCS_MIICTRL_ANE);
val &= ~PCS_MIICTRL_WB;
writel(val, gp->regs + PCS_MIICTRL);
val = readl(gp->regs + PCS_CFG);
val |= PCS_CFG_ENABLE;
writel(val, gp->regs + PCS_CFG);
/* Make sure serialink loopback is off. The meaning
* of this bit is logically inverted based upon whether
* you are in Serialink or SERDES mode.
*/
val = readl(gp->regs + PCS_SCTRL);
if (gp->phy_type == phy_serialink)
val &= ~PCS_SCTRL_LOOP;
else
val |= PCS_SCTRL_LOOP;
writel(val, gp->regs + PCS_SCTRL);
} }
/* Default aneg parameters */ /* Default aneg parameters */
...@@ -2680,6 +2697,21 @@ static int gem_get_settings(struct net_device *dev, struct ethtool_cmd *cmd) ...@@ -2680,6 +2697,21 @@ static int gem_get_settings(struct net_device *dev, struct ethtool_cmd *cmd)
cmd->speed = 0; cmd->speed = 0;
cmd->duplex = cmd->port = cmd->phy_address = cmd->duplex = cmd->port = cmd->phy_address =
cmd->transceiver = cmd->autoneg = 0; cmd->transceiver = cmd->autoneg = 0;
/* serdes means usually a Fibre connector, with most fixed */
if (gp->phy_type == phy_serdes) {
cmd->port = PORT_FIBRE;
cmd->supported = (SUPPORTED_1000baseT_Half |
SUPPORTED_1000baseT_Full |
SUPPORTED_FIBRE | SUPPORTED_Autoneg |
SUPPORTED_Pause | SUPPORTED_Asym_Pause);
cmd->advertising = cmd->supported;
cmd->transceiver = XCVR_INTERNAL;
if (gp->lstate == link_up)
cmd->speed = SPEED_1000;
cmd->duplex = DUPLEX_FULL;
cmd->autoneg = 1;
}
} }
cmd->maxtxpkt = cmd->maxrxpkt = 0; cmd->maxtxpkt = cmd->maxrxpkt = 0;
......
...@@ -334,6 +334,6 @@ static void __exit bfin_cf_exit(void) ...@@ -334,6 +334,6 @@ static void __exit bfin_cf_exit(void)
module_init(bfin_cf_init); module_init(bfin_cf_init);
module_exit(bfin_cf_exit); module_exit(bfin_cf_exit);
MODULE_AUTHOR("Michael Hennerich <hennerich@blackfin.uclinux.org>") MODULE_AUTHOR("Michael Hennerich <hennerich@blackfin.uclinux.org>");
MODULE_DESCRIPTION("BFIN CF/PCMCIA Driver"); MODULE_DESCRIPTION("BFIN CF/PCMCIA Driver");
MODULE_LICENSE("GPL"); MODULE_LICENSE("GPL");
...@@ -827,7 +827,7 @@ static int __init maple_bus_init(void) ...@@ -827,7 +827,7 @@ static int __init maple_bus_init(void)
maple_queue_cache = maple_queue_cache =
kmem_cache_create("maple_queue_cache", 0x400, 0, kmem_cache_create("maple_queue_cache", 0x400, 0,
SLAB_POISON|SLAB_HWCACHE_ALIGN, NULL); SLAB_HWCACHE_ALIGN, NULL);
if (!maple_queue_cache) if (!maple_queue_cache)
goto cleanup_bothirqs; goto cleanup_bothirqs;
......
...@@ -319,6 +319,7 @@ enum ...@@ -319,6 +319,7 @@ enum
{ {
NAPI_STATE_SCHED, /* Poll is scheduled */ NAPI_STATE_SCHED, /* Poll is scheduled */
NAPI_STATE_DISABLE, /* Disable pending */ NAPI_STATE_DISABLE, /* Disable pending */
NAPI_STATE_NPSVC, /* Netpoll - don't dequeue from poll_list */
}; };
extern void __napi_schedule(struct napi_struct *n); extern void __napi_schedule(struct napi_struct *n);
...@@ -1497,6 +1498,12 @@ static inline void netif_rx_complete(struct net_device *dev, ...@@ -1497,6 +1498,12 @@ static inline void netif_rx_complete(struct net_device *dev,
{ {
unsigned long flags; unsigned long flags;
/*
* don't let napi dequeue from the cpu poll list
* just in case its running on a different cpu
*/
if (unlikely(test_bit(NAPI_STATE_NPSVC, &napi->state)))
return;
local_irq_save(flags); local_irq_save(flags);
__netif_rx_complete(dev, napi); __netif_rx_complete(dev, napi);
local_irq_restore(flags); local_irq_restore(flags);
......
...@@ -146,6 +146,8 @@ static inline void smp_send_reschedule(int cpu) { } ...@@ -146,6 +146,8 @@ static inline void smp_send_reschedule(int cpu) { }
}) })
#define smp_call_function_mask(mask, func, info, wait) \ #define smp_call_function_mask(mask, func, info, wait) \
(up_smp_call_function(func, info)) (up_smp_call_function(func, info))
#define smp_call_function_many(mask, func, info, wait) \
(up_smp_call_function(func, info))
static inline void init_call_single_data(void) static inline void init_call_single_data(void)
{ {
} }
......
...@@ -702,7 +702,7 @@ static int rebind_subsystems(struct cgroupfs_root *root, ...@@ -702,7 +702,7 @@ static int rebind_subsystems(struct cgroupfs_root *root,
* any child cgroups exist. This is theoretically supportable * any child cgroups exist. This is theoretically supportable
* but involves complex error handling, so it's being left until * but involves complex error handling, so it's being left until
* later */ * later */
if (!list_empty(&cgrp->children)) if (root->number_of_cgroups > 1)
return -EBUSY; return -EBUSY;
/* Process each subsystem */ /* Process each subsystem */
......
...@@ -119,12 +119,12 @@ static u64 __update_sched_clock(struct sched_clock_data *scd, u64 now) ...@@ -119,12 +119,12 @@ static u64 __update_sched_clock(struct sched_clock_data *scd, u64 now)
/* /*
* scd->clock = clamp(scd->tick_gtod + delta, * scd->clock = clamp(scd->tick_gtod + delta,
* max(scd->tick_gtod, scd->clock), * max(scd->tick_gtod, scd->clock),
* max(scd->clock, scd->tick_gtod + TICK_NSEC)); * scd->tick_gtod + TICK_NSEC);
*/ */
clock = scd->tick_gtod + delta; clock = scd->tick_gtod + delta;
min_clock = wrap_max(scd->tick_gtod, scd->clock); min_clock = wrap_max(scd->tick_gtod, scd->clock);
max_clock = wrap_max(scd->clock, scd->tick_gtod + TICK_NSEC); max_clock = scd->tick_gtod + TICK_NSEC;
clock = wrap_max(clock, min_clock); clock = wrap_max(clock, min_clock);
clock = wrap_min(clock, max_clock); clock = wrap_min(clock, max_clock);
......
...@@ -998,7 +998,7 @@ static void do_pages_stat_array(struct mm_struct *mm, unsigned long nr_pages, ...@@ -998,7 +998,7 @@ static void do_pages_stat_array(struct mm_struct *mm, unsigned long nr_pages,
unsigned long addr = (unsigned long)(*pages); unsigned long addr = (unsigned long)(*pages);
struct vm_area_struct *vma; struct vm_area_struct *vma;
struct page *page; struct page *page;
int err; int err = -EFAULT;
vma = find_vma(mm, addr); vma = find_vma(mm, addr);
if (!vma) if (!vma)
......
...@@ -535,7 +535,7 @@ struct kmem_cache *kmem_cache_create(const char *name, size_t size, ...@@ -535,7 +535,7 @@ struct kmem_cache *kmem_cache_create(const char *name, size_t size,
struct kmem_cache *c; struct kmem_cache *c;
c = slob_alloc(sizeof(struct kmem_cache), c = slob_alloc(sizeof(struct kmem_cache),
flags, ARCH_KMALLOC_MINALIGN, -1); GFP_KERNEL, ARCH_KMALLOC_MINALIGN, -1);
if (c) { if (c) {
c->name = name; c->name = name;
......
...@@ -133,9 +133,11 @@ static int poll_one_napi(struct netpoll_info *npinfo, ...@@ -133,9 +133,11 @@ static int poll_one_napi(struct netpoll_info *npinfo,
npinfo->rx_flags |= NETPOLL_RX_DROP; npinfo->rx_flags |= NETPOLL_RX_DROP;
atomic_inc(&trapped); atomic_inc(&trapped);
set_bit(NAPI_STATE_NPSVC, &napi->state);
work = napi->poll(napi, budget); work = napi->poll(napi, budget);
clear_bit(NAPI_STATE_NPSVC, &napi->state);
atomic_dec(&trapped); atomic_dec(&trapped);
npinfo->rx_flags &= ~NETPOLL_RX_DROP; npinfo->rx_flags &= ~NETPOLL_RX_DROP;
......
...@@ -61,7 +61,7 @@ static struct ...@@ -61,7 +61,7 @@ static struct
static struct xt_table nat_table = { static struct xt_table nat_table = {
.name = "nat", .name = "nat",
.valid_hooks = NAT_VALID_HOOKS, .valid_hooks = NAT_VALID_HOOKS,
.lock = __RW_LOCK_UNLOCKED(__nat_table.lock), .lock = __RW_LOCK_UNLOCKED(nat_table.lock),
.me = THIS_MODULE, .me = THIS_MODULE,
.af = AF_INET, .af = AF_INET,
}; };
......
...@@ -40,18 +40,14 @@ ...@@ -40,18 +40,14 @@
#include "tcp_vegas.h" #include "tcp_vegas.h"
/* Default values of the Vegas variables, in fixed-point representation static int alpha = 2;
* with V_PARAM_SHIFT bits to the right of the binary point. static int beta = 4;
*/ static int gamma = 1;
#define V_PARAM_SHIFT 1
static int alpha = 2<<V_PARAM_SHIFT;
static int beta = 4<<V_PARAM_SHIFT;
static int gamma = 1<<V_PARAM_SHIFT;
module_param(alpha, int, 0644); module_param(alpha, int, 0644);
MODULE_PARM_DESC(alpha, "lower bound of packets in network (scale by 2)"); MODULE_PARM_DESC(alpha, "lower bound of packets in network");
module_param(beta, int, 0644); module_param(beta, int, 0644);
MODULE_PARM_DESC(beta, "upper bound of packets in network (scale by 2)"); MODULE_PARM_DESC(beta, "upper bound of packets in network");
module_param(gamma, int, 0644); module_param(gamma, int, 0644);
MODULE_PARM_DESC(gamma, "limit on increase (scale by 2)"); MODULE_PARM_DESC(gamma, "limit on increase (scale by 2)");
...@@ -172,49 +168,13 @@ static void tcp_vegas_cong_avoid(struct sock *sk, u32 ack, u32 in_flight) ...@@ -172,49 +168,13 @@ static void tcp_vegas_cong_avoid(struct sock *sk, u32 ack, u32 in_flight)
return; return;
} }
/* The key players are v_beg_snd_una and v_beg_snd_nxt.
*
* These are so named because they represent the approximate values
* of snd_una and snd_nxt at the beginning of the current RTT. More
* precisely, they represent the amount of data sent during the RTT.
* At the end of the RTT, when we receive an ACK for v_beg_snd_nxt,
* we will calculate that (v_beg_snd_nxt - v_beg_snd_una) outstanding
* bytes of data have been ACKed during the course of the RTT, giving
* an "actual" rate of:
*
* (v_beg_snd_nxt - v_beg_snd_una) / (rtt duration)
*
* Unfortunately, v_beg_snd_una is not exactly equal to snd_una,
* because delayed ACKs can cover more than one segment, so they
* don't line up nicely with the boundaries of RTTs.
*
* Another unfortunate fact of life is that delayed ACKs delay the
* advance of the left edge of our send window, so that the number
* of bytes we send in an RTT is often less than our cwnd will allow.
* So we keep track of our cwnd separately, in v_beg_snd_cwnd.
*/
if (after(ack, vegas->beg_snd_nxt)) { if (after(ack, vegas->beg_snd_nxt)) {
/* Do the Vegas once-per-RTT cwnd adjustment. */ /* Do the Vegas once-per-RTT cwnd adjustment. */
u32 old_wnd, old_snd_cwnd;
/* Here old_wnd is essentially the window of data that was
* sent during the previous RTT, and has all
* been acknowledged in the course of the RTT that ended
* with the ACK we just received. Likewise, old_snd_cwnd
* is the cwnd during the previous RTT.
*/
old_wnd = (vegas->beg_snd_nxt - vegas->beg_snd_una) /
tp->mss_cache;
old_snd_cwnd = vegas->beg_snd_cwnd;
/* Save the extent of the current window so we can use this /* Save the extent of the current window so we can use this
* at the end of the next RTT. * at the end of the next RTT.
*/ */
vegas->beg_snd_una = vegas->beg_snd_nxt;
vegas->beg_snd_nxt = tp->snd_nxt; vegas->beg_snd_nxt = tp->snd_nxt;
vegas->beg_snd_cwnd = tp->snd_cwnd;
/* We do the Vegas calculations only if we got enough RTT /* We do the Vegas calculations only if we got enough RTT
* samples that we can be reasonably sure that we got * samples that we can be reasonably sure that we got
...@@ -252,22 +212,14 @@ static void tcp_vegas_cong_avoid(struct sock *sk, u32 ack, u32 in_flight) ...@@ -252,22 +212,14 @@ static void tcp_vegas_cong_avoid(struct sock *sk, u32 ack, u32 in_flight)
* *
* This is: * This is:
* (actual rate in segments) * baseRTT * (actual rate in segments) * baseRTT
* We keep it as a fixed point number with
* V_PARAM_SHIFT bits to the right of the binary point.
*/ */
target_cwnd = ((u64)old_wnd * vegas->baseRTT); target_cwnd = tp->snd_cwnd * vegas->baseRTT / rtt;
target_cwnd <<= V_PARAM_SHIFT;
do_div(target_cwnd, rtt);
/* Calculate the difference between the window we had, /* Calculate the difference between the window we had,
* and the window we would like to have. This quantity * and the window we would like to have. This quantity
* is the "Diff" from the Arizona Vegas papers. * is the "Diff" from the Arizona Vegas papers.
*
* Again, this is a fixed point number with
* V_PARAM_SHIFT bits to the right of the binary
* point.
*/ */
diff = (old_wnd << V_PARAM_SHIFT) - target_cwnd; diff = tp->snd_cwnd * (rtt-vegas->baseRTT) / vegas->baseRTT;
if (diff > gamma && tp->snd_ssthresh > 2 ) { if (diff > gamma && tp->snd_ssthresh > 2 ) {
/* Going too fast. Time to slow down /* Going too fast. Time to slow down
...@@ -282,16 +234,13 @@ static void tcp_vegas_cong_avoid(struct sock *sk, u32 ack, u32 in_flight) ...@@ -282,16 +234,13 @@ static void tcp_vegas_cong_avoid(struct sock *sk, u32 ack, u32 in_flight)
* truncation robs us of full link * truncation robs us of full link
* utilization. * utilization.
*/ */
tp->snd_cwnd = min(tp->snd_cwnd, tp->snd_cwnd = min(tp->snd_cwnd, (u32)target_cwnd+1);
((u32)target_cwnd >>
V_PARAM_SHIFT)+1);
} else if (tp->snd_cwnd <= tp->snd_ssthresh) { } else if (tp->snd_cwnd <= tp->snd_ssthresh) {
/* Slow start. */ /* Slow start. */
tcp_slow_start(tp); tcp_slow_start(tp);
} else { } else {
/* Congestion avoidance. */ /* Congestion avoidance. */
u32 next_snd_cwnd;
/* Figure out where we would like cwnd /* Figure out where we would like cwnd
* to be. * to be.
...@@ -300,26 +249,17 @@ static void tcp_vegas_cong_avoid(struct sock *sk, u32 ack, u32 in_flight) ...@@ -300,26 +249,17 @@ static void tcp_vegas_cong_avoid(struct sock *sk, u32 ack, u32 in_flight)
/* The old window was too fast, so /* The old window was too fast, so
* we slow down. * we slow down.
*/ */
next_snd_cwnd = old_snd_cwnd - 1; tp->snd_cwnd--;
} else if (diff < alpha) { } else if (diff < alpha) {
/* We don't have enough extra packets /* We don't have enough extra packets
* in the network, so speed up. * in the network, so speed up.
*/ */
next_snd_cwnd = old_snd_cwnd + 1; tp->snd_cwnd++;
} else { } else {
/* Sending just as fast as we /* Sending just as fast as we
* should be. * should be.
*/ */
next_snd_cwnd = old_snd_cwnd;
} }
/* Adjust cwnd upward or downward, toward the
* desired value.
*/
if (next_snd_cwnd > tp->snd_cwnd)
tp->snd_cwnd++;
else if (next_snd_cwnd < tp->snd_cwnd)
tp->snd_cwnd--;
} }
if (tp->snd_cwnd < 2) if (tp->snd_cwnd < 2)
......
...@@ -912,7 +912,12 @@ static void ndisc_recv_na(struct sk_buff *skb) ...@@ -912,7 +912,12 @@ static void ndisc_recv_na(struct sk_buff *skb)
is invalid, but ndisc specs say nothing is invalid, but ndisc specs say nothing
about it. It could be misconfiguration, or about it. It could be misconfiguration, or
an smart proxy agent tries to help us :-) an smart proxy agent tries to help us :-)
We should not print the error if NA has been
received from loopback - it is just our own
unsolicited advertisement.
*/ */
if (skb->pkt_type != PACKET_LOOPBACK)
ND_PRINTK1(KERN_WARNING ND_PRINTK1(KERN_WARNING
"ICMPv6 NA: someone advertises our address on %s!\n", "ICMPv6 NA: someone advertises our address on %s!\n",
ifp->idev->dev->name); ifp->idev->dev->name);
......
...@@ -562,7 +562,6 @@ static int netlbl_unlhsh_remove_addr4(struct net *net, ...@@ -562,7 +562,6 @@ static int netlbl_unlhsh_remove_addr4(struct net *net,
const struct in_addr *mask, const struct in_addr *mask,
struct netlbl_audit *audit_info) struct netlbl_audit *audit_info)
{ {
int ret_val = 0;
struct netlbl_af4list *list_entry; struct netlbl_af4list *list_entry;
struct netlbl_unlhsh_addr4 *entry; struct netlbl_unlhsh_addr4 *entry;
struct audit_buffer *audit_buf; struct audit_buffer *audit_buf;
...@@ -577,7 +576,7 @@ static int netlbl_unlhsh_remove_addr4(struct net *net, ...@@ -577,7 +576,7 @@ static int netlbl_unlhsh_remove_addr4(struct net *net,
if (list_entry != NULL) if (list_entry != NULL)
entry = netlbl_unlhsh_addr4_entry(list_entry); entry = netlbl_unlhsh_addr4_entry(list_entry);
else else
ret_val = -ENOENT; entry = NULL;
audit_buf = netlbl_audit_start_common(AUDIT_MAC_UNLBL_STCDEL, audit_buf = netlbl_audit_start_common(AUDIT_MAC_UNLBL_STCDEL,
audit_info); audit_info);
...@@ -588,19 +587,21 @@ static int netlbl_unlhsh_remove_addr4(struct net *net, ...@@ -588,19 +587,21 @@ static int netlbl_unlhsh_remove_addr4(struct net *net,
addr->s_addr, mask->s_addr); addr->s_addr, mask->s_addr);
if (dev != NULL) if (dev != NULL)
dev_put(dev); dev_put(dev);
if (entry && security_secid_to_secctx(entry->secid, if (entry != NULL &&
&secctx, security_secid_to_secctx(entry->secid,
&secctx_len) == 0) { &secctx, &secctx_len) == 0) {
audit_log_format(audit_buf, " sec_obj=%s", secctx); audit_log_format(audit_buf, " sec_obj=%s", secctx);
security_release_secctx(secctx, secctx_len); security_release_secctx(secctx, secctx_len);
} }
audit_log_format(audit_buf, " res=%u", ret_val == 0 ? 1 : 0); audit_log_format(audit_buf, " res=%u", entry != NULL ? 1 : 0);
audit_log_end(audit_buf); audit_log_end(audit_buf);
} }
if (ret_val == 0) if (entry == NULL)
return -ENOENT;
call_rcu(&entry->rcu, netlbl_unlhsh_free_addr4); call_rcu(&entry->rcu, netlbl_unlhsh_free_addr4);
return ret_val; return 0;
} }
#if defined(CONFIG_IPV6) || defined(CONFIG_IPV6_MODULE) #if defined(CONFIG_IPV6) || defined(CONFIG_IPV6_MODULE)
...@@ -624,7 +625,6 @@ static int netlbl_unlhsh_remove_addr6(struct net *net, ...@@ -624,7 +625,6 @@ static int netlbl_unlhsh_remove_addr6(struct net *net,
const struct in6_addr *mask, const struct in6_addr *mask,
struct netlbl_audit *audit_info) struct netlbl_audit *audit_info)
{ {
int ret_val = 0;
struct netlbl_af6list *list_entry; struct netlbl_af6list *list_entry;
struct netlbl_unlhsh_addr6 *entry; struct netlbl_unlhsh_addr6 *entry;
struct audit_buffer *audit_buf; struct audit_buffer *audit_buf;
...@@ -638,7 +638,7 @@ static int netlbl_unlhsh_remove_addr6(struct net *net, ...@@ -638,7 +638,7 @@ static int netlbl_unlhsh_remove_addr6(struct net *net,
if (list_entry != NULL) if (list_entry != NULL)
entry = netlbl_unlhsh_addr6_entry(list_entry); entry = netlbl_unlhsh_addr6_entry(list_entry);
else else
ret_val = -ENOENT; entry = NULL;
audit_buf = netlbl_audit_start_common(AUDIT_MAC_UNLBL_STCDEL, audit_buf = netlbl_audit_start_common(AUDIT_MAC_UNLBL_STCDEL,
audit_info); audit_info);
...@@ -649,19 +649,21 @@ static int netlbl_unlhsh_remove_addr6(struct net *net, ...@@ -649,19 +649,21 @@ static int netlbl_unlhsh_remove_addr6(struct net *net,
addr, mask); addr, mask);
if (dev != NULL) if (dev != NULL)
dev_put(dev); dev_put(dev);
if (entry && security_secid_to_secctx(entry->secid, if (entry != NULL &&
&secctx, security_secid_to_secctx(entry->secid,
&secctx_len) == 0) { &secctx, &secctx_len) == 0) {
audit_log_format(audit_buf, " sec_obj=%s", secctx); audit_log_format(audit_buf, " sec_obj=%s", secctx);
security_release_secctx(secctx, secctx_len); security_release_secctx(secctx, secctx_len);
} }
audit_log_format(audit_buf, " res=%u", ret_val == 0 ? 1 : 0); audit_log_format(audit_buf, " res=%u", entry != NULL ? 1 : 0);
audit_log_end(audit_buf); audit_log_end(audit_buf);
} }
if (ret_val == 0) if (entry == NULL)
return -ENOENT;
call_rcu(&entry->rcu, netlbl_unlhsh_free_addr6); call_rcu(&entry->rcu, netlbl_unlhsh_free_addr6);
return ret_val; return 0;
} }
#endif /* IPv6 */ #endif /* IPv6 */
......
...@@ -155,12 +155,13 @@ static void gprs_data_ready(struct sock *sk, int len) ...@@ -155,12 +155,13 @@ static void gprs_data_ready(struct sock *sk, int len)
static void gprs_write_space(struct sock *sk) static void gprs_write_space(struct sock *sk)
{ {
struct gprs_dev *dev = sk->sk_user_data; struct gprs_dev *dev = sk->sk_user_data;
struct net_device *net = dev->net;
unsigned credits = pep_writeable(sk); unsigned credits = pep_writeable(sk);
spin_lock_bh(&dev->tx_lock); spin_lock_bh(&dev->tx_lock);
dev->tx_max = credits; dev->tx_max = credits;
if (credits > skb_queue_len(&dev->tx_queue)) if (credits > skb_queue_len(&dev->tx_queue) && netif_running(net))
netif_wake_queue(dev->net); netif_wake_queue(net);
spin_unlock_bh(&dev->tx_lock); spin_unlock_bh(&dev->tx_lock);
} }
...@@ -168,6 +169,23 @@ static void gprs_write_space(struct sock *sk) ...@@ -168,6 +169,23 @@ static void gprs_write_space(struct sock *sk)
* Network device callbacks * Network device callbacks
*/ */
static int gprs_open(struct net_device *dev)
{
struct gprs_dev *gp = netdev_priv(dev);
gprs_write_space(gp->sk);
return 0;
}
static int gprs_close(struct net_device *dev)
{
struct gprs_dev *gp = netdev_priv(dev);
netif_stop_queue(dev);
flush_work(&gp->tx_work);
return 0;
}
static int gprs_xmit(struct sk_buff *skb, struct net_device *net) static int gprs_xmit(struct sk_buff *skb, struct net_device *net)
{ {
struct gprs_dev *dev = netdev_priv(net); struct gprs_dev *dev = netdev_priv(net);
...@@ -254,6 +272,8 @@ static void gprs_setup(struct net_device *net) ...@@ -254,6 +272,8 @@ static void gprs_setup(struct net_device *net)
net->tx_queue_len = 10; net->tx_queue_len = 10;
net->destructor = free_netdev; net->destructor = free_netdev;
net->open = gprs_open;
net->stop = gprs_close;
net->hard_start_xmit = gprs_xmit; /* mandatory */ net->hard_start_xmit = gprs_xmit; /* mandatory */
net->change_mtu = gprs_set_mtu; net->change_mtu = gprs_set_mtu;
net->get_stats = gprs_get_stats; net->get_stats = gprs_get_stats;
...@@ -318,7 +338,6 @@ int gprs_attach(struct sock *sk) ...@@ -318,7 +338,6 @@ int gprs_attach(struct sock *sk)
dev->sk = sk; dev->sk = sk;
printk(KERN_DEBUG"%s: attached\n", net->name); printk(KERN_DEBUG"%s: attached\n", net->name);
gprs_write_space(sk); /* kick off TX */
return net->ifindex; return net->ifindex;
out_rel: out_rel:
...@@ -341,7 +360,5 @@ void gprs_detach(struct sock *sk) ...@@ -341,7 +360,5 @@ void gprs_detach(struct sock *sk)
printk(KERN_DEBUG"%s: detached\n", net->name); printk(KERN_DEBUG"%s: detached\n", net->name);
unregister_netdev(net); unregister_netdev(net);
flush_scheduled_work();
sock_put(sk); sock_put(sk);
skb_queue_purge(&dev->tx_queue);
} }
...@@ -46,9 +46,6 @@ ...@@ -46,9 +46,6 @@
layering other disciplines. It does not need to do bandwidth layering other disciplines. It does not need to do bandwidth
control either since that can be handled by using token control either since that can be handled by using token
bucket or other rate control. bucket or other rate control.
The simulator is limited by the Linux timer resolution
and will create packet bursts on the HZ boundary (1ms).
*/ */
struct netem_sched_data { struct netem_sched_data {
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment