summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAnthony G. Basile <blueness@gentoo.org>2011-12-25 16:53:44 -0500
committerAnthony G. Basile <blueness@gentoo.org>2011-12-25 16:53:44 -0500
commit581ff55f4dea2e36cc091c833958eccfa4975fd3 (patch)
treefcf9111ce9684267b2de3f3dcd8eaba703ff62c2
parentGrsec/PaX: 2.6.32.51-201112222105 + 3.1.6-201112222105 (diff)
downloadhardened-patchset-581ff55f4dea2e36cc091c833958eccfa4975fd3.tar.gz
hardened-patchset-581ff55f4dea2e36cc091c833958eccfa4975fd3.tar.bz2
hardened-patchset-581ff55f4dea2e36cc091c833958eccfa4975fd3.zip
Add patch to bump to 3.1.6
-rw-r--r--3.1.6/0000_README4
-rw-r--r--3.1.6/1005_linux-3.1.6.patch2178
2 files changed, 2182 insertions, 0 deletions
diff --git a/3.1.6/0000_README b/3.1.6/0000_README
index 29427c6..e8dbb91 100644
--- a/3.1.6/0000_README
+++ b/3.1.6/0000_README
@@ -3,6 +3,10 @@ README
Individual Patch Descriptions:
-----------------------------------------------------------------------------
+Patch: 1005_linux-3.1.6.patch
+From: http://www.kernel.org
+Desc: Linux 3.1.6
+
Patch: 4420_grsecurity-2.2.2-3.1.6-201112222105.patch
From: http://www.grsecurity.net
Desc: hardened-sources base patch from upstream grsecurity
diff --git a/3.1.6/1005_linux-3.1.6.patch b/3.1.6/1005_linux-3.1.6.patch
new file mode 100644
index 0000000..afd900d
--- /dev/null
+++ b/3.1.6/1005_linux-3.1.6.patch
@@ -0,0 +1,2178 @@
+diff --git a/Makefile b/Makefile
+index 94ab2ad..2d6e0a8 100644
+--- a/Makefile
++++ b/Makefile
+@@ -1,6 +1,6 @@
+ VERSION = 3
+ PATCHLEVEL = 1
+-SUBLEVEL = 5
++SUBLEVEL = 6
+ EXTRAVERSION =
+ NAME = "Divemaster Edition"
+
+diff --git a/arch/arm/kernel/setup.c b/arch/arm/kernel/setup.c
+index e514c76..3e42faf 100644
+--- a/arch/arm/kernel/setup.c
++++ b/arch/arm/kernel/setup.c
+@@ -890,6 +890,12 @@ void __init setup_arch(char **cmdline_p)
+ machine_desc = mdesc;
+ machine_name = mdesc->name;
+
++#ifdef CONFIG_ZONE_DMA
++ if (mdesc->dma_zone_size) {
++ extern unsigned long arm_dma_zone_size;
++ arm_dma_zone_size = mdesc->dma_zone_size;
++ }
++#endif
+ if (mdesc->soft_reboot)
+ reboot_setup("s");
+
+@@ -920,12 +926,6 @@ void __init setup_arch(char **cmdline_p)
+
+ tcm_init();
+
+-#ifdef CONFIG_ZONE_DMA
+- if (mdesc->dma_zone_size) {
+- extern unsigned long arm_dma_zone_size;
+- arm_dma_zone_size = mdesc->dma_zone_size;
+- }
+-#endif
+ #ifdef CONFIG_MULTI_IRQ_HANDLER
+ handle_arch_irq = mdesc->handle_irq;
+ #endif
+diff --git a/arch/arm/mach-at91/at91rm9200_devices.c b/arch/arm/mach-at91/at91rm9200_devices.c
+index 7227755..e596f45 100644
+--- a/arch/arm/mach-at91/at91rm9200_devices.c
++++ b/arch/arm/mach-at91/at91rm9200_devices.c
+@@ -75,7 +75,7 @@ void __init at91_add_device_usbh(struct at91_usbh_data *data) {}
+ * USB Device (Gadget)
+ * -------------------------------------------------------------------- */
+
+-#ifdef CONFIG_USB_GADGET_AT91
++#ifdef CONFIG_USB_AT91
+ static struct at91_udc_data udc_data;
+
+ static struct resource udc_resources[] = {
+diff --git a/arch/arm/mach-at91/at91sam9260.c b/arch/arm/mach-at91/at91sam9260.c
+index cb397be..de4036f 100644
+--- a/arch/arm/mach-at91/at91sam9260.c
++++ b/arch/arm/mach-at91/at91sam9260.c
+@@ -195,9 +195,9 @@ static struct clk_lookup periph_clocks_lookups[] = {
+ CLKDEV_CON_DEV_ID("t0_clk", "atmel_tcb.0", &tc0_clk),
+ CLKDEV_CON_DEV_ID("t1_clk", "atmel_tcb.0", &tc1_clk),
+ CLKDEV_CON_DEV_ID("t2_clk", "atmel_tcb.0", &tc2_clk),
+- CLKDEV_CON_DEV_ID("t3_clk", "atmel_tcb.1", &tc3_clk),
+- CLKDEV_CON_DEV_ID("t4_clk", "atmel_tcb.1", &tc4_clk),
+- CLKDEV_CON_DEV_ID("t5_clk", "atmel_tcb.1", &tc5_clk),
++ CLKDEV_CON_DEV_ID("t0_clk", "atmel_tcb.1", &tc3_clk),
++ CLKDEV_CON_DEV_ID("t1_clk", "atmel_tcb.1", &tc4_clk),
++ CLKDEV_CON_DEV_ID("t2_clk", "atmel_tcb.1", &tc5_clk),
+ CLKDEV_CON_DEV_ID("pclk", "ssc.0", &ssc_clk),
+ };
+
+diff --git a/arch/arm/mach-at91/at91sam9260_devices.c b/arch/arm/mach-at91/at91sam9260_devices.c
+index 39f81f4..ec257265 100644
+--- a/arch/arm/mach-at91/at91sam9260_devices.c
++++ b/arch/arm/mach-at91/at91sam9260_devices.c
+@@ -76,7 +76,7 @@ void __init at91_add_device_usbh(struct at91_usbh_data *data) {}
+ * USB Device (Gadget)
+ * -------------------------------------------------------------------- */
+
+-#ifdef CONFIG_USB_GADGET_AT91
++#ifdef CONFIG_USB_AT91
+ static struct at91_udc_data udc_data;
+
+ static struct resource udc_resources[] = {
+diff --git a/arch/arm/mach-at91/at91sam9261_devices.c b/arch/arm/mach-at91/at91sam9261_devices.c
+index 0f91792..9e113f6 100644
+--- a/arch/arm/mach-at91/at91sam9261_devices.c
++++ b/arch/arm/mach-at91/at91sam9261_devices.c
+@@ -79,7 +79,7 @@ void __init at91_add_device_usbh(struct at91_usbh_data *data) {}
+ * USB Device (Gadget)
+ * -------------------------------------------------------------------- */
+
+-#ifdef CONFIG_USB_GADGET_AT91
++#ifdef CONFIG_USB_AT91
+ static struct at91_udc_data udc_data;
+
+ static struct resource udc_resources[] = {
+diff --git a/arch/arm/mach-at91/at91sam9263_devices.c b/arch/arm/mach-at91/at91sam9263_devices.c
+index a050f41..863e466 100644
+--- a/arch/arm/mach-at91/at91sam9263_devices.c
++++ b/arch/arm/mach-at91/at91sam9263_devices.c
+@@ -86,7 +86,7 @@ void __init at91_add_device_usbh(struct at91_usbh_data *data) {}
+ * USB Device (Gadget)
+ * -------------------------------------------------------------------- */
+
+-#ifdef CONFIG_USB_GADGET_AT91
++#ifdef CONFIG_USB_AT91
+ static struct at91_udc_data udc_data;
+
+ static struct resource udc_resources[] = {
+diff --git a/arch/arm/mach-davinci/board-da850-evm.c b/arch/arm/mach-davinci/board-da850-evm.c
+index 008d514..d5ec333 100644
+--- a/arch/arm/mach-davinci/board-da850-evm.c
++++ b/arch/arm/mach-davinci/board-da850-evm.c
+@@ -748,7 +748,7 @@ static struct snd_platform_data da850_evm_snd_data = {
+ .num_serializer = ARRAY_SIZE(da850_iis_serializer_direction),
+ .tdm_slots = 2,
+ .serial_dir = da850_iis_serializer_direction,
+- .asp_chan_q = EVENTQ_1,
++ .asp_chan_q = EVENTQ_0,
+ .version = MCASP_VERSION_2,
+ .txnumevt = 1,
+ .rxnumevt = 1,
+diff --git a/arch/arm/mach-davinci/board-dm646x-evm.c b/arch/arm/mach-davinci/board-dm646x-evm.c
+index 993a314..1cc11d8 100644
+--- a/arch/arm/mach-davinci/board-dm646x-evm.c
++++ b/arch/arm/mach-davinci/board-dm646x-evm.c
+@@ -563,7 +563,7 @@ static int setup_vpif_input_channel_mode(int mux_mode)
+ int val;
+ u32 value;
+
+- if (!vpif_vsclkdis_reg || !cpld_client)
++ if (!vpif_vidclkctl_reg || !cpld_client)
+ return -ENXIO;
+
+ val = i2c_smbus_read_byte(cpld_client);
+@@ -571,7 +571,7 @@ static int setup_vpif_input_channel_mode(int mux_mode)
+ return val;
+
+ spin_lock_irqsave(&vpif_reg_lock, flags);
+- value = __raw_readl(vpif_vsclkdis_reg);
++ value = __raw_readl(vpif_vidclkctl_reg);
+ if (mux_mode) {
+ val &= VPIF_INPUT_TWO_CHANNEL;
+ value |= VIDCH1CLK;
+@@ -579,7 +579,7 @@ static int setup_vpif_input_channel_mode(int mux_mode)
+ val |= VPIF_INPUT_ONE_CHANNEL;
+ value &= ~VIDCH1CLK;
+ }
+- __raw_writel(value, vpif_vsclkdis_reg);
++ __raw_writel(value, vpif_vidclkctl_reg);
+ spin_unlock_irqrestore(&vpif_reg_lock, flags);
+
+ err = i2c_smbus_write_byte(cpld_client, val);
+diff --git a/arch/arm/mach-mxs/include/mach/mxs.h b/arch/arm/mach-mxs/include/mach/mxs.h
+index 35a89dd..1332f73 100644
+--- a/arch/arm/mach-mxs/include/mach/mxs.h
++++ b/arch/arm/mach-mxs/include/mach/mxs.h
+@@ -30,6 +30,7 @@
+ */
+ #define cpu_is_mx23() ( \
+ machine_is_mx23evk() || \
++ machine_is_stmp378x() || \
+ 0)
+ #define cpu_is_mx28() ( \
+ machine_is_mx28evk() || \
+diff --git a/arch/x86/include/asm/system.h b/arch/x86/include/asm/system.h
+index c2ff2a1..2d2f01c 100644
+--- a/arch/x86/include/asm/system.h
++++ b/arch/x86/include/asm/system.h
+@@ -401,6 +401,7 @@ extern unsigned long arch_align_stack(unsigned long sp);
+ extern void free_init_pages(char *what, unsigned long begin, unsigned long end);
+
+ void default_idle(void);
++bool set_pm_idle_to_default(void);
+
+ void stop_this_cpu(void *dummy);
+
+diff --git a/arch/x86/kernel/hpet.c b/arch/x86/kernel/hpet.c
+index 4aecc54..4d5a100 100644
+--- a/arch/x86/kernel/hpet.c
++++ b/arch/x86/kernel/hpet.c
+@@ -1048,6 +1048,14 @@ int hpet_rtc_timer_init(void)
+ }
+ EXPORT_SYMBOL_GPL(hpet_rtc_timer_init);
+
++static void hpet_disable_rtc_channel(void)
++{
++ unsigned long cfg;
++ cfg = hpet_readl(HPET_T1_CFG);
++ cfg &= ~HPET_TN_ENABLE;
++ hpet_writel(cfg, HPET_T1_CFG);
++}
++
+ /*
+ * The functions below are called from rtc driver.
+ * Return 0 if HPET is not being used.
+@@ -1059,6 +1067,9 @@ int hpet_mask_rtc_irq_bit(unsigned long bit_mask)
+ return 0;
+
+ hpet_rtc_flags &= ~bit_mask;
++ if (unlikely(!hpet_rtc_flags))
++ hpet_disable_rtc_channel();
++
+ return 1;
+ }
+ EXPORT_SYMBOL_GPL(hpet_mask_rtc_irq_bit);
+@@ -1124,15 +1135,11 @@ EXPORT_SYMBOL_GPL(hpet_rtc_dropped_irq);
+
+ static void hpet_rtc_timer_reinit(void)
+ {
+- unsigned int cfg, delta;
++ unsigned int delta;
+ int lost_ints = -1;
+
+- if (unlikely(!hpet_rtc_flags)) {
+- cfg = hpet_readl(HPET_T1_CFG);
+- cfg &= ~HPET_TN_ENABLE;
+- hpet_writel(cfg, HPET_T1_CFG);
+- return;
+- }
++ if (unlikely(!hpet_rtc_flags))
++ hpet_disable_rtc_channel();
+
+ if (!(hpet_rtc_flags & RTC_PIE) || hpet_pie_limit)
+ delta = hpet_default_delta;
+diff --git a/arch/x86/kernel/process.c b/arch/x86/kernel/process.c
+index e7e3b01..30eb651 100644
+--- a/arch/x86/kernel/process.c
++++ b/arch/x86/kernel/process.c
+@@ -403,6 +403,14 @@ void default_idle(void)
+ EXPORT_SYMBOL(default_idle);
+ #endif
+
++bool set_pm_idle_to_default(void)
++{
++ bool ret = !!pm_idle;
++
++ pm_idle = default_idle;
++
++ return ret;
++}
+ void stop_this_cpu(void *dummy)
+ {
+ local_irq_disable();
+diff --git a/arch/x86/mm/gup.c b/arch/x86/mm/gup.c
+index ea30585..dd74e46 100644
+--- a/arch/x86/mm/gup.c
++++ b/arch/x86/mm/gup.c
+@@ -201,6 +201,8 @@ static noinline int gup_huge_pud(pud_t pud, unsigned long addr,
+ do {
+ VM_BUG_ON(compound_head(page) != head);
+ pages[*nr] = page;
++ if (PageTail(page))
++ get_huge_page_tail(page);
+ (*nr)++;
+ page++;
+ refs++;
+diff --git a/arch/x86/xen/setup.c b/arch/x86/xen/setup.c
+index 46d6d21..e191302 100644
+--- a/arch/x86/xen/setup.c
++++ b/arch/x86/xen/setup.c
+@@ -191,9 +191,21 @@ static unsigned long __init xen_get_max_pages(void)
+ domid_t domid = DOMID_SELF;
+ int ret;
+
+- ret = HYPERVISOR_memory_op(XENMEM_maximum_reservation, &domid);
+- if (ret > 0)
+- max_pages = ret;
++ /*
++ * For the initial domain we use the maximum reservation as
++ * the maximum page.
++ *
++ * For guest domains the current maximum reservation reflects
++ * the current maximum rather than the static maximum. In this
++ * case the e820 map provided to us will cover the static
++ * maximum region.
++ */
++ if (xen_initial_domain()) {
++ ret = HYPERVISOR_memory_op(XENMEM_maximum_reservation, &domid);
++ if (ret > 0)
++ max_pages = ret;
++ }
++
+ return min(max_pages, MAX_DOMAIN_PAGES);
+ }
+
+@@ -448,6 +460,6 @@ void __init xen_arch_setup(void)
+ #endif
+ disable_cpuidle();
+ boot_option_idle_override = IDLE_HALT;
+-
++ WARN_ON(set_pm_idle_to_default());
+ fiddle_vdso();
+ }
+diff --git a/drivers/firmware/iscsi_ibft.c b/drivers/firmware/iscsi_ibft.c
+index c811cb1..2cce44a 100644
+--- a/drivers/firmware/iscsi_ibft.c
++++ b/drivers/firmware/iscsi_ibft.c
+@@ -746,6 +746,37 @@ static void __exit ibft_exit(void)
+ ibft_cleanup();
+ }
+
++#ifdef CONFIG_ACPI
++static const struct {
++ char *sign;
++} ibft_signs[] = {
++ /*
++ * One spec says "IBFT", the other says "iBFT". We have to check
++ * for both.
++ */
++ { ACPI_SIG_IBFT },
++ { "iBFT" },
++};
++
++static void __init acpi_find_ibft_region(void)
++{
++ int i;
++ struct acpi_table_header *table = NULL;
++
++ if (acpi_disabled)
++ return;
++
++ for (i = 0; i < ARRAY_SIZE(ibft_signs) && !ibft_addr; i++) {
++ acpi_get_table(ibft_signs[i].sign, 0, &table);
++ ibft_addr = (struct acpi_table_ibft *)table;
++ }
++}
++#else
++static void __init acpi_find_ibft_region(void)
++{
++}
++#endif
++
+ /*
+ * ibft_init() - creates sysfs tree entries for the iBFT data.
+ */
+@@ -753,9 +784,16 @@ static int __init ibft_init(void)
+ {
+ int rc = 0;
+
++ /*
++ As on UEFI systems the setup_arch()/find_ibft_region()
++ is called before ACPI tables are parsed and it only does
++ legacy finding.
++ */
++ if (!ibft_addr)
++ acpi_find_ibft_region();
++
+ if (ibft_addr) {
+- printk(KERN_INFO "iBFT detected at 0x%llx.\n",
+- (u64)isa_virt_to_bus(ibft_addr));
++ pr_info("iBFT detected.\n");
+
+ rc = ibft_check_device();
+ if (rc)
+diff --git a/drivers/firmware/iscsi_ibft_find.c b/drivers/firmware/iscsi_ibft_find.c
+index bfe7232..4da4eb9 100644
+--- a/drivers/firmware/iscsi_ibft_find.c
++++ b/drivers/firmware/iscsi_ibft_find.c
+@@ -45,13 +45,6 @@ EXPORT_SYMBOL_GPL(ibft_addr);
+ static const struct {
+ char *sign;
+ } ibft_signs[] = {
+-#ifdef CONFIG_ACPI
+- /*
+- * One spec says "IBFT", the other says "iBFT". We have to check
+- * for both.
+- */
+- { ACPI_SIG_IBFT },
+-#endif
+ { "iBFT" },
+ { "BIFT" }, /* Broadcom iSCSI Offload */
+ };
+@@ -62,14 +55,6 @@ static const struct {
+ #define VGA_MEM 0xA0000 /* VGA buffer */
+ #define VGA_SIZE 0x20000 /* 128kB */
+
+-#ifdef CONFIG_ACPI
+-static int __init acpi_find_ibft(struct acpi_table_header *header)
+-{
+- ibft_addr = (struct acpi_table_ibft *)header;
+- return 0;
+-}
+-#endif /* CONFIG_ACPI */
+-
+ static int __init find_ibft_in_mem(void)
+ {
+ unsigned long pos;
+@@ -94,6 +79,7 @@ static int __init find_ibft_in_mem(void)
+ * the table cannot be valid. */
+ if (pos + len <= (IBFT_END-1)) {
+ ibft_addr = (struct acpi_table_ibft *)virt;
++ pr_info("iBFT found at 0x%lx.\n", pos);
+ goto done;
+ }
+ }
+@@ -108,20 +94,12 @@ done:
+ */
+ unsigned long __init find_ibft_region(unsigned long *sizep)
+ {
+-#ifdef CONFIG_ACPI
+- int i;
+-#endif
+ ibft_addr = NULL;
+
+-#ifdef CONFIG_ACPI
+- for (i = 0; i < ARRAY_SIZE(ibft_signs) && !ibft_addr; i++)
+- acpi_table_parse(ibft_signs[i].sign, acpi_find_ibft);
+-#endif /* CONFIG_ACPI */
+-
+ /* iBFT 1.03 section 1.4.3.1 mandates that UEFI machines will
+ * only use ACPI for this */
+
+- if (!ibft_addr && !efi_enabled)
++ if (!efi_enabled)
+ find_ibft_in_mem();
+
+ if (ibft_addr) {
+diff --git a/drivers/gpu/drm/radeon/atombios_crtc.c b/drivers/gpu/drm/radeon/atombios_crtc.c
+index a515b2a..9bb3d6f 100644
+--- a/drivers/gpu/drm/radeon/atombios_crtc.c
++++ b/drivers/gpu/drm/radeon/atombios_crtc.c
+@@ -558,7 +558,7 @@ static u32 atombios_adjust_pll(struct drm_crtc *crtc,
+ bpc = connector->display_info.bpc;
+ encoder_mode = atombios_get_encoder_mode(encoder);
+ if ((radeon_encoder->devices & (ATOM_DEVICE_LCD_SUPPORT | ATOM_DEVICE_DFP_SUPPORT)) ||
+- radeon_encoder_is_dp_bridge(encoder)) {
++ (radeon_encoder_get_dp_bridge_encoder_id(encoder) != ENCODER_OBJECT_ID_NONE)) {
+ if (connector) {
+ struct radeon_connector *radeon_connector = to_radeon_connector(connector);
+ struct radeon_connector_atom_dig *dig_connector =
+@@ -638,44 +638,29 @@ static u32 atombios_adjust_pll(struct drm_crtc *crtc,
+ if (ss_enabled && ss->percentage)
+ args.v3.sInput.ucDispPllConfig |=
+ DISPPLL_CONFIG_SS_ENABLE;
+- if (radeon_encoder->devices & (ATOM_DEVICE_DFP_SUPPORT) ||
+- radeon_encoder_is_dp_bridge(encoder)) {
++ if (encoder_mode == ATOM_ENCODER_MODE_DP) {
++ args.v3.sInput.ucDispPllConfig |=
++ DISPPLL_CONFIG_COHERENT_MODE;
++ /* 16200 or 27000 */
++ args.v3.sInput.usPixelClock = cpu_to_le16(dp_clock / 10);
++ } else if (radeon_encoder->devices & (ATOM_DEVICE_DFP_SUPPORT)) {
+ struct radeon_encoder_atom_dig *dig = radeon_encoder->enc_priv;
+- if (encoder_mode == ATOM_ENCODER_MODE_DP) {
++ if (encoder_mode == ATOM_ENCODER_MODE_HDMI)
++ /* deep color support */
++ args.v3.sInput.usPixelClock =
++ cpu_to_le16((mode->clock * bpc / 8) / 10);
++ if (dig->coherent_mode)
+ args.v3.sInput.ucDispPllConfig |=
+ DISPPLL_CONFIG_COHERENT_MODE;
+- /* 16200 or 27000 */
+- args.v3.sInput.usPixelClock = cpu_to_le16(dp_clock / 10);
+- } else {
+- if (encoder_mode == ATOM_ENCODER_MODE_HDMI) {
+- /* deep color support */
+- args.v3.sInput.usPixelClock =
+- cpu_to_le16((mode->clock * bpc / 8) / 10);
+- }
+- if (dig->coherent_mode)
+- args.v3.sInput.ucDispPllConfig |=
+- DISPPLL_CONFIG_COHERENT_MODE;
+- if (mode->clock > 165000)
+- args.v3.sInput.ucDispPllConfig |=
+- DISPPLL_CONFIG_DUAL_LINK;
+- }
+- } else if (radeon_encoder->devices & (ATOM_DEVICE_LCD_SUPPORT)) {
+- if (encoder_mode == ATOM_ENCODER_MODE_DP) {
++ if (mode->clock > 165000)
+ args.v3.sInput.ucDispPllConfig |=
+- DISPPLL_CONFIG_COHERENT_MODE;
+- /* 16200 or 27000 */
+- args.v3.sInput.usPixelClock = cpu_to_le16(dp_clock / 10);
+- } else if (encoder_mode != ATOM_ENCODER_MODE_LVDS) {
+- if (mode->clock > 165000)
+- args.v3.sInput.ucDispPllConfig |=
+- DISPPLL_CONFIG_DUAL_LINK;
+- }
++ DISPPLL_CONFIG_DUAL_LINK;
+ }
+- if (radeon_encoder_is_dp_bridge(encoder)) {
+- struct drm_encoder *ext_encoder = radeon_atom_get_external_encoder(encoder);
+- struct radeon_encoder *ext_radeon_encoder = to_radeon_encoder(ext_encoder);
+- args.v3.sInput.ucExtTransmitterID = ext_radeon_encoder->encoder_id;
+- } else
++ if (radeon_encoder_get_dp_bridge_encoder_id(encoder) !=
++ ENCODER_OBJECT_ID_NONE)
++ args.v3.sInput.ucExtTransmitterID =
++ radeon_encoder_get_dp_bridge_encoder_id(encoder);
++ else
+ args.v3.sInput.ucExtTransmitterID = 0;
+
+ atom_execute_table(rdev->mode_info.atom_context,
+diff --git a/drivers/gpu/drm/radeon/atombios_dp.c b/drivers/gpu/drm/radeon/atombios_dp.c
+index 3b77ad6..03a347a 100644
+--- a/drivers/gpu/drm/radeon/atombios_dp.c
++++ b/drivers/gpu/drm/radeon/atombios_dp.c
+@@ -482,7 +482,8 @@ static int radeon_dp_get_dp_link_clock(struct drm_connector *connector,
+ int bpp = convert_bpc_to_bpp(connector->display_info.bpc);
+ int lane_num, max_pix_clock;
+
+- if (radeon_connector_encoder_is_dp_bridge(connector))
++ if (radeon_connector_encoder_get_dp_bridge_encoder_id(connector) !=
++ ENCODER_OBJECT_ID_NONE)
+ return 270000;
+
+ lane_num = radeon_dp_get_dp_lane_number(connector, dpcd, pix_clock);
+@@ -559,8 +560,12 @@ static void radeon_dp_set_panel_mode(struct drm_encoder *encoder,
+ if (!ASIC_IS_DCE4(rdev))
+ return;
+
+- if (radeon_connector_encoder_is_dp_bridge(connector))
++ if (radeon_connector_encoder_get_dp_bridge_encoder_id(connector) ==
++ ENCODER_OBJECT_ID_NUTMEG)
+ panel_mode = DP_PANEL_MODE_INTERNAL_DP1_MODE;
++ else if (radeon_connector_encoder_get_dp_bridge_encoder_id(connector) ==
++ ENCODER_OBJECT_ID_TRAVIS)
++ panel_mode = DP_PANEL_MODE_INTERNAL_DP2_MODE;
+ else if (connector->connector_type == DRM_MODE_CONNECTOR_eDP) {
+ u8 tmp = radeon_read_dpcd_reg(radeon_connector, DP_EDP_CONFIGURATION_CAP);
+ if (tmp & 1)
+diff --git a/drivers/gpu/drm/radeon/radeon_connectors.c b/drivers/gpu/drm/radeon/radeon_connectors.c
+index ff6a2e0..a58b452 100644
+--- a/drivers/gpu/drm/radeon/radeon_connectors.c
++++ b/drivers/gpu/drm/radeon/radeon_connectors.c
+@@ -44,8 +44,6 @@ extern void
+ radeon_legacy_backlight_init(struct radeon_encoder *radeon_encoder,
+ struct drm_connector *drm_connector);
+
+-bool radeon_connector_encoder_is_dp_bridge(struct drm_connector *connector);
+-
+ void radeon_connector_hotplug(struct drm_connector *connector)
+ {
+ struct drm_device *dev = connector->dev;
+@@ -1204,7 +1202,8 @@ static int radeon_dp_get_modes(struct drm_connector *connector)
+ }
+ } else {
+ /* need to setup ddc on the bridge */
+- if (radeon_connector_encoder_is_dp_bridge(connector)) {
++ if (radeon_connector_encoder_get_dp_bridge_encoder_id(connector) !=
++ ENCODER_OBJECT_ID_NONE) {
+ if (encoder)
+ radeon_atom_ext_encoder_setup_ddc(encoder);
+ }
+@@ -1214,13 +1213,12 @@ static int radeon_dp_get_modes(struct drm_connector *connector)
+ return ret;
+ }
+
+-bool radeon_connector_encoder_is_dp_bridge(struct drm_connector *connector)
++u16 radeon_connector_encoder_get_dp_bridge_encoder_id(struct drm_connector *connector)
+ {
+ struct drm_mode_object *obj;
+ struct drm_encoder *encoder;
+ struct radeon_encoder *radeon_encoder;
+ int i;
+- bool found = false;
+
+ for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++) {
+ if (connector->encoder_ids[i] == 0)
+@@ -1236,14 +1234,13 @@ bool radeon_connector_encoder_is_dp_bridge(struct drm_connector *connector)
+ switch (radeon_encoder->encoder_id) {
+ case ENCODER_OBJECT_ID_TRAVIS:
+ case ENCODER_OBJECT_ID_NUTMEG:
+- found = true;
+- break;
++ return radeon_encoder->encoder_id;
+ default:
+ break;
+ }
+ }
+
+- return found;
++ return ENCODER_OBJECT_ID_NONE;
+ }
+
+ bool radeon_connector_encoder_is_hbr2(struct drm_connector *connector)
+@@ -1320,7 +1317,8 @@ radeon_dp_detect(struct drm_connector *connector, bool force)
+ if (!radeon_dig_connector->edp_on)
+ atombios_set_edp_panel_power(connector,
+ ATOM_TRANSMITTER_ACTION_POWER_OFF);
+- } else if (radeon_connector_encoder_is_dp_bridge(connector)) {
++ } else if (radeon_connector_encoder_get_dp_bridge_encoder_id(connector) !=
++ ENCODER_OBJECT_ID_NONE) {
+ /* DP bridges are always DP */
+ radeon_dig_connector->dp_sink_type = CONNECTOR_OBJECT_ID_DISPLAYPORT;
+ /* get the DPCD from the bridge */
+diff --git a/drivers/gpu/drm/radeon/radeon_display.c b/drivers/gpu/drm/radeon/radeon_display.c
+index 6adb3e5..07ac481 100644
+--- a/drivers/gpu/drm/radeon/radeon_display.c
++++ b/drivers/gpu/drm/radeon/radeon_display.c
+@@ -708,7 +708,8 @@ int radeon_ddc_get_modes(struct radeon_connector *radeon_connector)
+
+ if ((radeon_connector->base.connector_type == DRM_MODE_CONNECTOR_DisplayPort) ||
+ (radeon_connector->base.connector_type == DRM_MODE_CONNECTOR_eDP) ||
+- radeon_connector_encoder_is_dp_bridge(&radeon_connector->base)) {
++ (radeon_connector_encoder_get_dp_bridge_encoder_id(&radeon_connector->base) !=
++ ENCODER_OBJECT_ID_NONE)) {
+ struct radeon_connector_atom_dig *dig = radeon_connector->con_priv;
+
+ if ((dig->dp_sink_type == CONNECTOR_OBJECT_ID_DISPLAYPORT ||
+diff --git a/drivers/gpu/drm/radeon/radeon_encoders.c b/drivers/gpu/drm/radeon/radeon_encoders.c
+index eb3f6dc..9838865 100644
+--- a/drivers/gpu/drm/radeon/radeon_encoders.c
++++ b/drivers/gpu/drm/radeon/radeon_encoders.c
+@@ -266,7 +266,7 @@ struct drm_encoder *radeon_atom_get_external_encoder(struct drm_encoder *encoder
+ return NULL;
+ }
+
+-bool radeon_encoder_is_dp_bridge(struct drm_encoder *encoder)
++u16 radeon_encoder_get_dp_bridge_encoder_id(struct drm_encoder *encoder)
+ {
+ struct drm_encoder *other_encoder = radeon_atom_get_external_encoder(encoder);
+
+@@ -368,7 +368,7 @@ static bool radeon_atom_mode_fixup(struct drm_encoder *encoder,
+
+ if (ASIC_IS_DCE3(rdev) &&
+ ((radeon_encoder->active_device & (ATOM_DEVICE_DFP_SUPPORT | ATOM_DEVICE_LCD_SUPPORT)) ||
+- radeon_encoder_is_dp_bridge(encoder))) {
++ (radeon_encoder_get_dp_bridge_encoder_id(encoder) != ENCODER_OBJECT_ID_NONE))) {
+ struct drm_connector *connector = radeon_get_connector_for_encoder(encoder);
+ radeon_dp_set_link_config(connector, mode);
+ }
+@@ -658,7 +658,7 @@ atombios_get_encoder_mode(struct drm_encoder *encoder)
+ struct radeon_connector_atom_dig *dig_connector;
+
+ /* dp bridges are always DP */
+- if (radeon_encoder_is_dp_bridge(encoder))
++ if (radeon_encoder_get_dp_bridge_encoder_id(encoder) != ENCODER_OBJECT_ID_NONE)
+ return ATOM_ENCODER_MODE_DP;
+
+ /* DVO is always DVO */
+@@ -1638,7 +1638,7 @@ atombios_set_encoder_crtc_source(struct drm_encoder *encoder)
+ break;
+ case 2:
+ args.v2.ucCRTC = radeon_crtc->crtc_id;
+- if (radeon_encoder_is_dp_bridge(encoder)) {
++ if (radeon_encoder_get_dp_bridge_encoder_id(encoder) != ENCODER_OBJECT_ID_NONE) {
+ struct drm_connector *connector = radeon_get_connector_for_encoder(encoder);
+
+ if (connector->connector_type == DRM_MODE_CONNECTOR_LVDS)
+@@ -2099,7 +2099,8 @@ static void radeon_atom_encoder_prepare(struct drm_encoder *encoder)
+
+ if ((radeon_encoder->active_device &
+ (ATOM_DEVICE_DFP_SUPPORT | ATOM_DEVICE_LCD_SUPPORT)) ||
+- radeon_encoder_is_dp_bridge(encoder)) {
++ (radeon_encoder_get_dp_bridge_encoder_id(encoder) !=
++ ENCODER_OBJECT_ID_NONE)) {
+ struct radeon_encoder_atom_dig *dig = radeon_encoder->enc_priv;
+ if (dig)
+ dig->dig_encoder = radeon_atom_pick_dig_encoder(encoder);
+diff --git a/drivers/gpu/drm/radeon/radeon_mode.h b/drivers/gpu/drm/radeon/radeon_mode.h
+index ed0178f..cbf80de 100644
+--- a/drivers/gpu/drm/radeon/radeon_mode.h
++++ b/drivers/gpu/drm/radeon/radeon_mode.h
+@@ -468,8 +468,8 @@ radeon_atombios_get_tv_info(struct radeon_device *rdev);
+ extern struct drm_connector *
+ radeon_get_connector_for_encoder(struct drm_encoder *encoder);
+
+-extern bool radeon_encoder_is_dp_bridge(struct drm_encoder *encoder);
+-extern bool radeon_connector_encoder_is_dp_bridge(struct drm_connector *connector);
++extern u16 radeon_encoder_get_dp_bridge_encoder_id(struct drm_encoder *encoder);
++extern u16 radeon_connector_encoder_get_dp_bridge_encoder_id(struct drm_connector *connector);
+ extern bool radeon_connector_encoder_is_hbr2(struct drm_connector *connector);
+ extern bool radeon_connector_is_dp12_capable(struct drm_connector *connector);
+
+diff --git a/drivers/hwmon/jz4740-hwmon.c b/drivers/hwmon/jz4740-hwmon.c
+index fea292d..b65a4da 100644
+--- a/drivers/hwmon/jz4740-hwmon.c
++++ b/drivers/hwmon/jz4740-hwmon.c
+@@ -59,7 +59,7 @@ static ssize_t jz4740_hwmon_read_adcin(struct device *dev,
+ {
+ struct jz4740_hwmon *hwmon = dev_get_drvdata(dev);
+ struct completion *completion = &hwmon->read_completion;
+- unsigned long t;
++ long t;
+ unsigned long val;
+ int ret;
+
+diff --git a/drivers/mmc/host/mxcmmc.c b/drivers/mmc/host/mxcmmc.c
+index 14aa213..b87143d 100644
+--- a/drivers/mmc/host/mxcmmc.c
++++ b/drivers/mmc/host/mxcmmc.c
+@@ -731,6 +731,7 @@ static void mxcmci_set_ios(struct mmc_host *mmc, struct mmc_ios *ios)
+ "failed to config DMA channel. Falling back to PIO\n");
+ dma_release_channel(host->dma);
+ host->do_dma = 0;
++ host->dma = NULL;
+ }
+ }
+
+diff --git a/drivers/ptp/ptp_clock.c b/drivers/ptp/ptp_clock.c
+index cf3f999..10451a1 100644
+--- a/drivers/ptp/ptp_clock.c
++++ b/drivers/ptp/ptp_clock.c
+@@ -101,7 +101,9 @@ static s32 scaled_ppm_to_ppb(long ppm)
+
+ static int ptp_clock_getres(struct posix_clock *pc, struct timespec *tp)
+ {
+- return 1; /* always round timer functions to one nanosecond */
++ tp->tv_sec = 0;
++ tp->tv_nsec = 1;
++ return 0;
+ }
+
+ static int ptp_clock_settime(struct posix_clock *pc, const struct timespec *tp)
+diff --git a/drivers/rtc/rtc-s3c.c b/drivers/rtc/rtc-s3c.c
+index 7639ab9..5b979d9 100644
+--- a/drivers/rtc/rtc-s3c.c
++++ b/drivers/rtc/rtc-s3c.c
+@@ -202,7 +202,6 @@ static int s3c_rtc_settime(struct device *dev, struct rtc_time *tm)
+ void __iomem *base = s3c_rtc_base;
+ int year = tm->tm_year - 100;
+
+- clk_enable(rtc_clk);
+ pr_debug("set time %04d.%02d.%02d %02d:%02d:%02d\n",
+ 1900 + tm->tm_year, tm->tm_mon, tm->tm_mday,
+ tm->tm_hour, tm->tm_min, tm->tm_sec);
+@@ -214,6 +213,7 @@ static int s3c_rtc_settime(struct device *dev, struct rtc_time *tm)
+ return -EINVAL;
+ }
+
++ clk_enable(rtc_clk);
+ writeb(bin2bcd(tm->tm_sec), base + S3C2410_RTCSEC);
+ writeb(bin2bcd(tm->tm_min), base + S3C2410_RTCMIN);
+ writeb(bin2bcd(tm->tm_hour), base + S3C2410_RTCHOUR);
+diff --git a/drivers/staging/rtl8712/usb_intf.c b/drivers/staging/rtl8712/usb_intf.c
+index 21ce2af..6cb7e28 100644
+--- a/drivers/staging/rtl8712/usb_intf.c
++++ b/drivers/staging/rtl8712/usb_intf.c
+@@ -86,6 +86,7 @@ static struct usb_device_id rtl871x_usb_id_tbl[] = {
+ {USB_DEVICE(0x0DF6, 0x0045)},
+ {USB_DEVICE(0x0DF6, 0x0059)}, /* 11n mode disable */
+ {USB_DEVICE(0x0DF6, 0x004B)},
++ {USB_DEVICE(0x0DF6, 0x005D)},
+ {USB_DEVICE(0x0DF6, 0x0063)},
+ /* Sweex */
+ {USB_DEVICE(0x177F, 0x0154)},
+diff --git a/drivers/target/iscsi/iscsi_target.c b/drivers/target/iscsi/iscsi_target.c
+index 26a5d8b..c4ac6f6 100644
+--- a/drivers/target/iscsi/iscsi_target.c
++++ b/drivers/target/iscsi/iscsi_target.c
+@@ -1043,6 +1043,8 @@ done:
+ */
+ send_check_condition = 1;
+ } else {
++ cmd->data_length = cmd->se_cmd.data_length;
++
+ if (iscsit_decide_list_to_build(cmd, payload_length) < 0)
+ return iscsit_add_reject_from_cmd(
+ ISCSI_REASON_BOOKMARK_NO_RESOURCES,
+@@ -2512,10 +2514,10 @@ static int iscsit_send_data_in(
+ if (hdr->flags & ISCSI_FLAG_DATA_STATUS) {
+ if (cmd->se_cmd.se_cmd_flags & SCF_OVERFLOW_BIT) {
+ hdr->flags |= ISCSI_FLAG_DATA_OVERFLOW;
+- hdr->residual_count = cpu_to_be32(cmd->residual_count);
++ hdr->residual_count = cpu_to_be32(cmd->se_cmd.residual_count);
+ } else if (cmd->se_cmd.se_cmd_flags & SCF_UNDERFLOW_BIT) {
+ hdr->flags |= ISCSI_FLAG_DATA_UNDERFLOW;
+- hdr->residual_count = cpu_to_be32(cmd->residual_count);
++ hdr->residual_count = cpu_to_be32(cmd->se_cmd.residual_count);
+ }
+ }
+ hton24(hdr->dlength, datain.length);
+@@ -3017,10 +3019,10 @@ static int iscsit_send_status(
+ hdr->flags |= ISCSI_FLAG_CMD_FINAL;
+ if (cmd->se_cmd.se_cmd_flags & SCF_OVERFLOW_BIT) {
+ hdr->flags |= ISCSI_FLAG_CMD_OVERFLOW;
+- hdr->residual_count = cpu_to_be32(cmd->residual_count);
++ hdr->residual_count = cpu_to_be32(cmd->se_cmd.residual_count);
+ } else if (cmd->se_cmd.se_cmd_flags & SCF_UNDERFLOW_BIT) {
+ hdr->flags |= ISCSI_FLAG_CMD_UNDERFLOW;
+- hdr->residual_count = cpu_to_be32(cmd->residual_count);
++ hdr->residual_count = cpu_to_be32(cmd->se_cmd.residual_count);
+ }
+ hdr->response = cmd->iscsi_response;
+ hdr->cmd_status = cmd->se_cmd.scsi_status;
+@@ -3132,6 +3134,7 @@ static int iscsit_send_task_mgt_rsp(
+ hdr = (struct iscsi_tm_rsp *) cmd->pdu;
+ memset(hdr, 0, ISCSI_HDR_LEN);
+ hdr->opcode = ISCSI_OP_SCSI_TMFUNC_RSP;
++ hdr->flags = ISCSI_FLAG_CMD_FINAL;
+ hdr->response = iscsit_convert_tcm_tmr_rsp(se_tmr);
+ hdr->itt = cpu_to_be32(cmd->init_task_tag);
+ cmd->stat_sn = conn->stat_sn++;
+diff --git a/drivers/target/iscsi/iscsi_target_core.h b/drivers/target/iscsi/iscsi_target_core.h
+index 470ed55..8d18b2c 100644
+--- a/drivers/target/iscsi/iscsi_target_core.h
++++ b/drivers/target/iscsi/iscsi_target_core.h
+@@ -395,7 +395,6 @@ struct iscsi_cmd {
+ u32 pdu_send_order;
+ /* Current struct iscsi_pdu in struct iscsi_cmd->pdu_list */
+ u32 pdu_start;
+- u32 residual_count;
+ /* Next struct iscsi_seq to send in struct iscsi_cmd->seq_list */
+ u32 seq_send_order;
+ /* Number of struct iscsi_seq in struct iscsi_cmd->seq_list */
+diff --git a/drivers/target/target_core_cdb.c b/drivers/target/target_core_cdb.c
+index f04d4ef..5f91397 100644
+--- a/drivers/target/target_core_cdb.c
++++ b/drivers/target/target_core_cdb.c
+@@ -477,7 +477,7 @@ target_emulate_evpd_86(struct se_cmd *cmd, unsigned char *buf)
+ if (cmd->data_length < 60)
+ return 0;
+
+- buf[2] = 0x3c;
++ buf[3] = 0x3c;
+ /* Set HEADSUP, ORDSUP, SIMPSUP */
+ buf[5] = 0x07;
+
+diff --git a/drivers/target/target_core_file.c b/drivers/target/target_core_file.c
+index bc1b336..ceb2a28 100644
+--- a/drivers/target/target_core_file.c
++++ b/drivers/target/target_core_file.c
+@@ -288,9 +288,9 @@ static int fd_do_readv(struct se_task *task)
+ return -ENOMEM;
+ }
+
+- for (i = 0; i < task->task_sg_nents; i++) {
+- iov[i].iov_len = sg[i].length;
+- iov[i].iov_base = sg_virt(&sg[i]);
++ for_each_sg(task->task_sg, sg, task->task_sg_nents, i) {
++ iov[i].iov_len = sg->length;
++ iov[i].iov_base = sg_virt(sg);
+ }
+
+ old_fs = get_fs();
+@@ -340,9 +340,9 @@ static int fd_do_writev(struct se_task *task)
+ return -ENOMEM;
+ }
+
+- for (i = 0; i < task->task_sg_nents; i++) {
+- iov[i].iov_len = sg[i].length;
+- iov[i].iov_base = sg_virt(&sg[i]);
++ for_each_sg(task->task_sg, sg, task->task_sg_nents, i) {
++ iov[i].iov_len = sg->length;
++ iov[i].iov_base = sg_virt(sg);
+ }
+
+ old_fs = get_fs();
+diff --git a/drivers/target/target_core_transport.c b/drivers/target/target_core_transport.c
+index 013c100..e2added 100644
+--- a/drivers/target/target_core_transport.c
++++ b/drivers/target/target_core_transport.c
+@@ -2562,10 +2562,15 @@ static inline u32 transport_get_sectors_6(
+
+ /*
+ * Everything else assume TYPE_DISK Sector CDB location.
+- * Use 8-bit sector value.
++ * Use 8-bit sector value. SBC-3 says:
++ *
++ * A TRANSFER LENGTH field set to zero specifies that 256
++ * logical blocks shall be written. Any other value
++ * specifies the number of logical blocks that shall be
++ * written.
+ */
+ type_disk:
+- return (u32)cdb[4];
++ return cdb[4] ? : 256;
+ }
+
+ static inline u32 transport_get_sectors_10(
+@@ -3873,6 +3878,18 @@ int transport_generic_map_mem_to_cmd(
+
+ if ((cmd->se_cmd_flags & SCF_SCSI_DATA_SG_IO_CDB) ||
+ (cmd->se_cmd_flags & SCF_SCSI_CONTROL_SG_IO_CDB)) {
++ /*
++ * Reject SCSI data overflow with map_mem_to_cmd() as incoming
++ * scatterlists already have been set to follow what the fabric
++ * passes for the original expected data transfer length.
++ */
++ if (cmd->se_cmd_flags & SCF_OVERFLOW_BIT) {
++ pr_warn("Rejecting SCSI DATA overflow for fabric using"
++ " SCF_PASSTHROUGH_SG_TO_MEM_NOALLOC\n");
++ cmd->se_cmd_flags |= SCF_SCSI_CDB_EXCEPTION;
++ cmd->scsi_sense_reason = TCM_INVALID_CDB_FIELD;
++ return -EINVAL;
++ }
+
+ cmd->t_data_sg = sgl;
+ cmd->t_data_nents = sgl_count;
+diff --git a/drivers/usb/class/cdc-acm.c b/drivers/usb/class/cdc-acm.c
+index 2ffcaa0..8faa23c 100644
+--- a/drivers/usb/class/cdc-acm.c
++++ b/drivers/usb/class/cdc-acm.c
+@@ -1458,6 +1458,16 @@ static const struct usb_device_id acm_ids[] = {
+ },
+ { USB_DEVICE(0x22b8, 0x6425), /* Motorola MOTOMAGX phones */
+ },
++ /* Motorola H24 HSPA module: */
++ { USB_DEVICE(0x22b8, 0x2d91) }, /* modem */
++ { USB_DEVICE(0x22b8, 0x2d92) }, /* modem + diagnostics */
++ { USB_DEVICE(0x22b8, 0x2d93) }, /* modem + AT port */
++ { USB_DEVICE(0x22b8, 0x2d95) }, /* modem + AT port + diagnostics */
++ { USB_DEVICE(0x22b8, 0x2d96) }, /* modem + NMEA */
++ { USB_DEVICE(0x22b8, 0x2d97) }, /* modem + diagnostics + NMEA */
++ { USB_DEVICE(0x22b8, 0x2d99) }, /* modem + AT port + NMEA */
++ { USB_DEVICE(0x22b8, 0x2d9a) }, /* modem + AT port + diagnostics + NMEA */
++
+ { USB_DEVICE(0x0572, 0x1329), /* Hummingbird huc56s (Conexant) */
+ .driver_info = NO_UNION_NORMAL, /* union descriptor misplaced on
+ data interface instead of
+diff --git a/drivers/usb/serial/option.c b/drivers/usb/serial/option.c
+index e98a1e1..d2becb9 100644
+--- a/drivers/usb/serial/option.c
++++ b/drivers/usb/serial/option.c
+@@ -659,7 +659,12 @@ static const struct usb_device_id option_ids[] = {
+ { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E353, 0xff, 0x01, 0x01) },
+ { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E353, 0xff, 0x01, 0x02) },
+ { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E353, 0xff, 0x01, 0x03) },
+- { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E353, 0xff, 0x01, 0x08) },
++ { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E353, 0xff, 0x01, 0x10) },
++ { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E353, 0xff, 0x01, 0x12) },
++ { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E353, 0xff, 0x01, 0x13) },
++ { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E353, 0xff, 0x02, 0x01) }, /* E398 3G Modem */
++ { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E353, 0xff, 0x02, 0x02) }, /* E398 3G PC UI Interface */
++ { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E353, 0xff, 0x02, 0x03) }, /* E398 3G Application Interface */
+ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, NOVATELWIRELESS_PRODUCT_V640) },
+ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, NOVATELWIRELESS_PRODUCT_V620) },
+ { USB_DEVICE(NOVATELWIRELESS_VENDOR_ID, NOVATELWIRELESS_PRODUCT_V740) },
+diff --git a/fs/cifs/readdir.c b/fs/cifs/readdir.c
+index 5de03ec..a090bbe 100644
+--- a/fs/cifs/readdir.c
++++ b/fs/cifs/readdir.c
+@@ -554,7 +554,10 @@ static int find_cifs_entry(const int xid, struct cifs_tcon *pTcon,
+ rc);
+ return rc;
+ }
+- cifs_save_resume_key(cifsFile->srch_inf.last_entry, cifsFile);
++ /* FindFirst/Next set last_entry to NULL on malformed reply */
++ if (cifsFile->srch_inf.last_entry)
++ cifs_save_resume_key(cifsFile->srch_inf.last_entry,
++ cifsFile);
+ }
+
+ while ((index_to_find >= cifsFile->srch_inf.index_of_last_entry) &&
+@@ -562,7 +565,10 @@ static int find_cifs_entry(const int xid, struct cifs_tcon *pTcon,
+ cFYI(1, "calling findnext2");
+ rc = CIFSFindNext(xid, pTcon, cifsFile->netfid,
+ &cifsFile->srch_inf);
+- cifs_save_resume_key(cifsFile->srch_inf.last_entry, cifsFile);
++ /* FindFirst/Next set last_entry to NULL on malformed reply */
++ if (cifsFile->srch_inf.last_entry)
++ cifs_save_resume_key(cifsFile->srch_inf.last_entry,
++ cifsFile);
+ if (rc)
+ return -ENOENT;
+ }
+diff --git a/fs/dcache.c b/fs/dcache.c
+index a88948b..8b732a2 100644
+--- a/fs/dcache.c
++++ b/fs/dcache.c
+@@ -2398,16 +2398,14 @@ static int prepend_name(char **buffer, int *buflen, struct qstr *name)
+ /**
+ * prepend_path - Prepend path string to a buffer
+ * @path: the dentry/vfsmount to report
+- * @root: root vfsmnt/dentry (may be modified by this function)
++ * @root: root vfsmnt/dentry
+ * @buffer: pointer to the end of the buffer
+ * @buflen: pointer to buffer length
+ *
+ * Caller holds the rename_lock.
+- *
+- * If path is not reachable from the supplied root, then the value of
+- * root is changed (without modifying refcounts).
+ */
+-static int prepend_path(const struct path *path, struct path *root,
++static int prepend_path(const struct path *path,
++ const struct path *root,
+ char **buffer, int *buflen)
+ {
+ struct dentry *dentry = path->dentry;
+@@ -2442,10 +2440,10 @@ static int prepend_path(const struct path *path, struct path *root,
+ dentry = parent;
+ }
+
+-out:
+ if (!error && !slash)
+ error = prepend(buffer, buflen, "/", 1);
+
++out:
+ br_read_unlock(vfsmount_lock);
+ return error;
+
+@@ -2459,15 +2457,17 @@ global_root:
+ WARN(1, "Root dentry has weird name <%.*s>\n",
+ (int) dentry->d_name.len, dentry->d_name.name);
+ }
+- root->mnt = vfsmnt;
+- root->dentry = dentry;
++ if (!slash)
++ error = prepend(buffer, buflen, "/", 1);
++ if (!error)
++ error = vfsmnt->mnt_ns ? 1 : 2;
+ goto out;
+ }
+
+ /**
+ * __d_path - return the path of a dentry
+ * @path: the dentry/vfsmount to report
+- * @root: root vfsmnt/dentry (may be modified by this function)
++ * @root: root vfsmnt/dentry
+ * @buf: buffer to return value in
+ * @buflen: buffer length
+ *
+@@ -2478,10 +2478,10 @@ global_root:
+ *
+ * "buflen" should be positive.
+ *
+- * If path is not reachable from the supplied root, then the value of
+- * root is changed (without modifying refcounts).
++ * If the path is not reachable from the supplied root, return %NULL.
+ */
+-char *__d_path(const struct path *path, struct path *root,
++char *__d_path(const struct path *path,
++ const struct path *root,
+ char *buf, int buflen)
+ {
+ char *res = buf + buflen;
+@@ -2492,7 +2492,28 @@ char *__d_path(const struct path *path, struct path *root,
+ error = prepend_path(path, root, &res, &buflen);
+ write_sequnlock(&rename_lock);
+
+- if (error)
++ if (error < 0)
++ return ERR_PTR(error);
++ if (error > 0)
++ return NULL;
++ return res;
++}
++
++char *d_absolute_path(const struct path *path,
++ char *buf, int buflen)
++{
++ struct path root = {};
++ char *res = buf + buflen;
++ int error;
++
++ prepend(&res, &buflen, "\0", 1);
++ write_seqlock(&rename_lock);
++ error = prepend_path(path, &root, &res, &buflen);
++ write_sequnlock(&rename_lock);
++
++ if (error > 1)
++ error = -EINVAL;
++ if (error < 0)
+ return ERR_PTR(error);
+ return res;
+ }
+@@ -2500,8 +2521,9 @@ char *__d_path(const struct path *path, struct path *root,
+ /*
+ * same as __d_path but appends "(deleted)" for unlinked files.
+ */
+-static int path_with_deleted(const struct path *path, struct path *root,
+- char **buf, int *buflen)
++static int path_with_deleted(const struct path *path,
++ const struct path *root,
++ char **buf, int *buflen)
+ {
+ prepend(buf, buflen, "\0", 1);
+ if (d_unlinked(path->dentry)) {
+@@ -2538,7 +2560,6 @@ char *d_path(const struct path *path, char *buf, int buflen)
+ {
+ char *res = buf + buflen;
+ struct path root;
+- struct path tmp;
+ int error;
+
+ /*
+@@ -2553,9 +2574,8 @@ char *d_path(const struct path *path, char *buf, int buflen)
+
+ get_fs_root(current->fs, &root);
+ write_seqlock(&rename_lock);
+- tmp = root;
+- error = path_with_deleted(path, &tmp, &res, &buflen);
+- if (error)
++ error = path_with_deleted(path, &root, &res, &buflen);
++ if (error < 0)
+ res = ERR_PTR(error);
+ write_sequnlock(&rename_lock);
+ path_put(&root);
+@@ -2576,7 +2596,6 @@ char *d_path_with_unreachable(const struct path *path, char *buf, int buflen)
+ {
+ char *res = buf + buflen;
+ struct path root;
+- struct path tmp;
+ int error;
+
+ if (path->dentry->d_op && path->dentry->d_op->d_dname)
+@@ -2584,9 +2603,8 @@ char *d_path_with_unreachable(const struct path *path, char *buf, int buflen)
+
+ get_fs_root(current->fs, &root);
+ write_seqlock(&rename_lock);
+- tmp = root;
+- error = path_with_deleted(path, &tmp, &res, &buflen);
+- if (!error && !path_equal(&tmp, &root))
++ error = path_with_deleted(path, &root, &res, &buflen);
++ if (error > 0)
+ error = prepend_unreachable(&res, &buflen);
+ write_sequnlock(&rename_lock);
+ path_put(&root);
+@@ -2717,19 +2735,18 @@ SYSCALL_DEFINE2(getcwd, char __user *, buf, unsigned long, size)
+ write_seqlock(&rename_lock);
+ if (!d_unlinked(pwd.dentry)) {
+ unsigned long len;
+- struct path tmp = root;
+ char *cwd = page + PAGE_SIZE;
+ int buflen = PAGE_SIZE;
+
+ prepend(&cwd, &buflen, "\0", 1);
+- error = prepend_path(&pwd, &tmp, &cwd, &buflen);
++ error = prepend_path(&pwd, &root, &cwd, &buflen);
+ write_sequnlock(&rename_lock);
+
+- if (error)
++ if (error < 0)
+ goto out;
+
+ /* Unreachable from current root */
+- if (!path_equal(&tmp, &root)) {
++ if (error > 0) {
+ error = prepend_unreachable(&cwd, &buflen);
+ if (error)
+ goto out;
+diff --git a/fs/ext4/inode.c b/fs/ext4/inode.c
+index b644b9c..5dbdb6b 100644
+--- a/fs/ext4/inode.c
++++ b/fs/ext4/inode.c
+@@ -1261,8 +1261,11 @@ static int mpage_da_submit_io(struct mpage_da_data *mpd,
+ clear_buffer_unwritten(bh);
+ }
+
+- /* skip page if block allocation undone */
+- if (buffer_delay(bh) || buffer_unwritten(bh))
++ /*
++ * skip page if block allocation undone and
++ * block is dirty
++ */
++ if (ext4_bh_delay_or_unwritten(NULL, bh))
+ skip_page = 1;
+ bh = bh->b_this_page;
+ block_start += bh->b_size;
+@@ -2367,7 +2370,7 @@ static int ext4_da_write_end(struct file *file,
+ */
+
+ new_i_size = pos + copied;
+- if (new_i_size > EXT4_I(inode)->i_disksize) {
++ if (copied && new_i_size > EXT4_I(inode)->i_disksize) {
+ if (ext4_da_should_update_i_disksize(page, end)) {
+ down_write(&EXT4_I(inode)->i_data_sem);
+ if (new_i_size > EXT4_I(inode)->i_disksize) {
+@@ -2630,10 +2633,11 @@ static void ext4_end_io_dio(struct kiocb *iocb, loff_t offset,
+ iocb->private, io_end->inode->i_ino, iocb, offset,
+ size);
+
++ iocb->private = NULL;
++
+ /* if not aio dio with unwritten extents, just free io and return */
+ if (!(io_end->flag & EXT4_IO_END_UNWRITTEN)) {
+ ext4_free_io_end(io_end);
+- iocb->private = NULL;
+ out:
+ if (is_async)
+ aio_complete(iocb, ret, 0);
+@@ -2656,7 +2660,6 @@ out:
+ spin_unlock_irqrestore(&ei->i_completed_io_lock, flags);
+
+ /* queue the work to convert unwritten extents to written */
+- iocb->private = NULL;
+ queue_work(wq, &io_end->work);
+
+ /* XXX: probably should move into the real I/O completion handler */
+diff --git a/fs/ext4/page-io.c b/fs/ext4/page-io.c
+index 92f38ee..78ab854 100644
+--- a/fs/ext4/page-io.c
++++ b/fs/ext4/page-io.c
+@@ -401,6 +401,18 @@ int ext4_bio_write_page(struct ext4_io_submit *io,
+
+ block_end = block_start + blocksize;
+ if (block_start >= len) {
++ /*
++ * Comments copied from block_write_full_page_endio:
++ *
++ * The page straddles i_size. It must be zeroed out on
++ * each and every writepage invocation because it may
++ * be mmapped. "A file is mapped in multiples of the
++ * page size. For a file that is not a multiple of
++ * the page size, the remaining memory is zeroed when
++ * mapped, and writes to that region are not written
++ * out to the file."
++ */
++ zero_user_segment(page, block_start, block_end);
+ clear_buffer_dirty(bh);
+ set_buffer_uptodate(bh);
+ continue;
+diff --git a/fs/ext4/super.c b/fs/ext4/super.c
+index 44d0c8d..065ff37 100644
+--- a/fs/ext4/super.c
++++ b/fs/ext4/super.c
+@@ -1140,9 +1140,9 @@ static int ext4_show_options(struct seq_file *seq, struct vfsmount *vfs)
+ seq_puts(seq, ",block_validity");
+
+ if (!test_opt(sb, INIT_INODE_TABLE))
+- seq_puts(seq, ",noinit_inode_table");
++ seq_puts(seq, ",noinit_itable");
+ else if (sbi->s_li_wait_mult != EXT4_DEF_LI_WAIT_MULT)
+- seq_printf(seq, ",init_inode_table=%u",
++ seq_printf(seq, ",init_itable=%u",
+ (unsigned) sbi->s_li_wait_mult);
+
+ ext4_show_quota_options(seq, sb);
+@@ -1318,8 +1318,7 @@ enum {
+ Opt_nomblk_io_submit, Opt_block_validity, Opt_noblock_validity,
+ Opt_inode_readahead_blks, Opt_journal_ioprio,
+ Opt_dioread_nolock, Opt_dioread_lock,
+- Opt_discard, Opt_nodiscard,
+- Opt_init_inode_table, Opt_noinit_inode_table,
++ Opt_discard, Opt_nodiscard, Opt_init_itable, Opt_noinit_itable,
+ };
+
+ static const match_table_t tokens = {
+@@ -1392,9 +1391,9 @@ static const match_table_t tokens = {
+ {Opt_dioread_lock, "dioread_lock"},
+ {Opt_discard, "discard"},
+ {Opt_nodiscard, "nodiscard"},
+- {Opt_init_inode_table, "init_itable=%u"},
+- {Opt_init_inode_table, "init_itable"},
+- {Opt_noinit_inode_table, "noinit_itable"},
++ {Opt_init_itable, "init_itable=%u"},
++ {Opt_init_itable, "init_itable"},
++ {Opt_noinit_itable, "noinit_itable"},
+ {Opt_err, NULL},
+ };
+
+@@ -1871,7 +1870,7 @@ set_qf_format:
+ case Opt_dioread_lock:
+ clear_opt(sb, DIOREAD_NOLOCK);
+ break;
+- case Opt_init_inode_table:
++ case Opt_init_itable:
+ set_opt(sb, INIT_INODE_TABLE);
+ if (args[0].from) {
+ if (match_int(&args[0], &option))
+@@ -1882,7 +1881,7 @@ set_qf_format:
+ return 0;
+ sbi->s_li_wait_mult = option;
+ break;
+- case Opt_noinit_inode_table:
++ case Opt_noinit_itable:
+ clear_opt(sb, INIT_INODE_TABLE);
+ break;
+ default:
+diff --git a/fs/fuse/dev.c b/fs/fuse/dev.c
+index 5cb8614..2aaf3ea 100644
+--- a/fs/fuse/dev.c
++++ b/fs/fuse/dev.c
+@@ -1512,7 +1512,7 @@ static int fuse_retrieve(struct fuse_conn *fc, struct inode *inode,
+ else if (outarg->offset + num > file_size)
+ num = file_size - outarg->offset;
+
+- while (num) {
++ while (num && req->num_pages < FUSE_MAX_PAGES_PER_REQ) {
+ struct page *page;
+ unsigned int this_num;
+
+@@ -1526,6 +1526,7 @@ static int fuse_retrieve(struct fuse_conn *fc, struct inode *inode,
+
+ num -= this_num;
+ total_len += this_num;
++ index++;
+ }
+ req->misc.retrieve_in.offset = outarg->offset;
+ req->misc.retrieve_in.size = total_len;
+diff --git a/fs/fuse/file.c b/fs/fuse/file.c
+index 594f07a..19029e9 100644
+--- a/fs/fuse/file.c
++++ b/fs/fuse/file.c
+@@ -1556,7 +1556,7 @@ static loff_t fuse_file_llseek(struct file *file, loff_t offset, int origin)
+ struct inode *inode = file->f_path.dentry->d_inode;
+
+ mutex_lock(&inode->i_mutex);
+- if (origin != SEEK_CUR || origin != SEEK_SET) {
++ if (origin != SEEK_CUR && origin != SEEK_SET) {
+ retval = fuse_update_attributes(inode, NULL, file, NULL);
+ if (retval)
+ goto exit;
+diff --git a/fs/hfs/btree.c b/fs/hfs/btree.c
+index 3ebc437..1cbdeea 100644
+--- a/fs/hfs/btree.c
++++ b/fs/hfs/btree.c
+@@ -46,11 +46,26 @@ struct hfs_btree *hfs_btree_open(struct super_block *sb, u32 id, btree_keycmp ke
+ case HFS_EXT_CNID:
+ hfs_inode_read_fork(tree->inode, mdb->drXTExtRec, mdb->drXTFlSize,
+ mdb->drXTFlSize, be32_to_cpu(mdb->drXTClpSiz));
++ if (HFS_I(tree->inode)->alloc_blocks >
++ HFS_I(tree->inode)->first_blocks) {
++ printk(KERN_ERR "hfs: invalid btree extent records\n");
++ unlock_new_inode(tree->inode);
++ goto free_inode;
++ }
++
+ tree->inode->i_mapping->a_ops = &hfs_btree_aops;
+ break;
+ case HFS_CAT_CNID:
+ hfs_inode_read_fork(tree->inode, mdb->drCTExtRec, mdb->drCTFlSize,
+ mdb->drCTFlSize, be32_to_cpu(mdb->drCTClpSiz));
++
++ if (!HFS_I(tree->inode)->first_blocks) {
++ printk(KERN_ERR "hfs: invalid btree extent records "
++ "(0 size).\n");
++ unlock_new_inode(tree->inode);
++ goto free_inode;
++ }
++
+ tree->inode->i_mapping->a_ops = &hfs_btree_aops;
+ break;
+ default:
+@@ -59,11 +74,6 @@ struct hfs_btree *hfs_btree_open(struct super_block *sb, u32 id, btree_keycmp ke
+ }
+ unlock_new_inode(tree->inode);
+
+- if (!HFS_I(tree->inode)->first_blocks) {
+- printk(KERN_ERR "hfs: invalid btree extent records (0 size).\n");
+- goto free_inode;
+- }
+-
+ mapping = tree->inode->i_mapping;
+ page = read_mapping_page(mapping, 0, NULL);
+ if (IS_ERR(page))
+diff --git a/fs/jbd/journal.c b/fs/jbd/journal.c
+index 9fe061f..fea8dd6 100644
+--- a/fs/jbd/journal.c
++++ b/fs/jbd/journal.c
+@@ -1135,6 +1135,14 @@ static int journal_get_superblock(journal_t *journal)
+ goto out;
+ }
+
++ if (be32_to_cpu(sb->s_first) == 0 ||
++ be32_to_cpu(sb->s_first) >= journal->j_maxlen) {
++ printk(KERN_WARNING
++ "JBD: Invalid start block of journal: %u\n",
++ be32_to_cpu(sb->s_first));
++ goto out;
++ }
++
+ return 0;
+
+ out:
+diff --git a/fs/jbd2/journal.c b/fs/jbd2/journal.c
+index f24df13..d6e93d0 100644
+--- a/fs/jbd2/journal.c
++++ b/fs/jbd2/journal.c
+@@ -1251,6 +1251,14 @@ static int journal_get_superblock(journal_t *journal)
+ goto out;
+ }
+
++ if (be32_to_cpu(sb->s_first) == 0 ||
++ be32_to_cpu(sb->s_first) >= journal->j_maxlen) {
++ printk(KERN_WARNING
++ "JBD2: Invalid start block of journal: %u\n",
++ be32_to_cpu(sb->s_first));
++ goto out;
++ }
++
+ return 0;
+
+ out:
+diff --git a/fs/namespace.c b/fs/namespace.c
+index e5e1c7d..5e7f2e9 100644
+--- a/fs/namespace.c
++++ b/fs/namespace.c
+@@ -1048,15 +1048,12 @@ static int show_mountinfo(struct seq_file *m, void *v)
+ if (err)
+ goto out;
+ seq_putc(m, ' ');
+- seq_path_root(m, &mnt_path, &root, " \t\n\\");
+- if (root.mnt != p->root.mnt || root.dentry != p->root.dentry) {
+- /*
+- * Mountpoint is outside root, discard that one. Ugly,
+- * but less so than trying to do that in iterator in a
+- * race-free way (due to renames).
+- */
+- return SEQ_SKIP;
+- }
++
++ /* mountpoints outside of chroot jail will give SEQ_SKIP on this */
++ err = seq_path_root(m, &mnt_path, &root, " \t\n\\");
++ if (err)
++ goto out;
++
+ seq_puts(m, mnt->mnt_flags & MNT_READONLY ? " ro" : " rw");
+ show_mnt_opts(m, mnt);
+
+@@ -2744,3 +2741,8 @@ void kern_unmount(struct vfsmount *mnt)
+ }
+ }
+ EXPORT_SYMBOL(kern_unmount);
++
++bool our_mnt(struct vfsmount *mnt)
++{
++ return check_mnt(mnt);
++}
+diff --git a/fs/proc/meminfo.c b/fs/proc/meminfo.c
+index 5861741..80e4645 100644
+--- a/fs/proc/meminfo.c
++++ b/fs/proc/meminfo.c
+@@ -131,12 +131,13 @@ static int meminfo_proc_show(struct seq_file *m, void *v)
+ K(i.freeswap),
+ K(global_page_state(NR_FILE_DIRTY)),
+ K(global_page_state(NR_WRITEBACK)),
+- K(global_page_state(NR_ANON_PAGES)
+ #ifdef CONFIG_TRANSPARENT_HUGEPAGE
++ K(global_page_state(NR_ANON_PAGES)
+ + global_page_state(NR_ANON_TRANSPARENT_HUGEPAGES) *
+- HPAGE_PMD_NR
++ HPAGE_PMD_NR),
++#else
++ K(global_page_state(NR_ANON_PAGES)),
+ #endif
+- ),
+ K(global_page_state(NR_FILE_MAPPED)),
+ K(global_page_state(NR_SHMEM)),
+ K(global_page_state(NR_SLAB_RECLAIMABLE) +
+diff --git a/fs/seq_file.c b/fs/seq_file.c
+index 05d6b0e..dba43c3 100644
+--- a/fs/seq_file.c
++++ b/fs/seq_file.c
+@@ -449,8 +449,6 @@ EXPORT_SYMBOL(seq_path);
+
+ /*
+ * Same as seq_path, but relative to supplied root.
+- *
+- * root may be changed, see __d_path().
+ */
+ int seq_path_root(struct seq_file *m, struct path *path, struct path *root,
+ char *esc)
+@@ -463,6 +461,8 @@ int seq_path_root(struct seq_file *m, struct path *path, struct path *root,
+ char *p;
+
+ p = __d_path(path, root, buf, size);
++ if (!p)
++ return SEQ_SKIP;
+ res = PTR_ERR(p);
+ if (!IS_ERR(p)) {
+ char *end = mangle_path(buf, p, esc);
+@@ -474,7 +474,7 @@ int seq_path_root(struct seq_file *m, struct path *path, struct path *root,
+ }
+ seq_commit(m, res);
+
+- return res < 0 ? res : 0;
++ return res < 0 && res != -ENAMETOOLONG ? res : 0;
+ }
+
+ /*
+diff --git a/include/drm/drm_pciids.h b/include/drm/drm_pciids.h
+index 4e4fbb8..14b6cd0 100644
+--- a/include/drm/drm_pciids.h
++++ b/include/drm/drm_pciids.h
+@@ -182,8 +182,11 @@
+ {0x1002, 0x6748, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_TURKS|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x6749, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_TURKS|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x6750, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_TURKS|RADEON_NEW_MEMMAP}, \
++ {0x1002, 0x6751, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_TURKS|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x6758, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_TURKS|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x6759, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_TURKS|RADEON_NEW_MEMMAP}, \
++ {0x1002, 0x675B, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_TURKS|RADEON_NEW_MEMMAP}, \
++ {0x1002, 0x675D, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_TURKS|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x675F, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_TURKS|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x6760, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_CAICOS|RADEON_IS_MOBILITY|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x6761, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_CAICOS|RADEON_IS_MOBILITY|RADEON_NEW_MEMMAP}, \
+@@ -195,8 +198,10 @@
+ {0x1002, 0x6767, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_CAICOS|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x6768, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_CAICOS|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x6770, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_CAICOS|RADEON_NEW_MEMMAP}, \
++ {0x1002, 0x6772, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_CAICOS|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x6778, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_CAICOS|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x6779, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_CAICOS|RADEON_NEW_MEMMAP}, \
++ {0x1002, 0x677B, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_CAICOS|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x6840, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_TURKS|RADEON_IS_MOBILITY|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x6841, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_TURKS|RADEON_IS_MOBILITY|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x6842, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_TURKS|RADEON_IS_MOBILITY|RADEON_NEW_MEMMAP}, \
+@@ -246,6 +251,7 @@
+ {0x1002, 0x68f2, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_CEDAR|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x68f8, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_CEDAR|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x68f9, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_CEDAR|RADEON_NEW_MEMMAP}, \
++ {0x1002, 0x68fa, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_CEDAR|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x68fe, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_CEDAR|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x7100, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_R520|RADEON_NEW_MEMMAP}, \
+ {0x1002, 0x7101, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_R520|RADEON_IS_MOBILITY|RADEON_NEW_MEMMAP}, \
+@@ -488,6 +494,8 @@
+ {0x1002, 0x9647, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_SUMO|RADEON_IS_MOBILITY|RADEON_NEW_MEMMAP|RADEON_IS_IGP},\
+ {0x1002, 0x9648, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_SUMO|RADEON_IS_MOBILITY|RADEON_NEW_MEMMAP|RADEON_IS_IGP},\
+ {0x1002, 0x964a, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_SUMO|RADEON_NEW_MEMMAP|RADEON_IS_IGP}, \
++ {0x1002, 0x964b, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_SUMO|RADEON_NEW_MEMMAP|RADEON_IS_IGP}, \
++ {0x1002, 0x964c, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_SUMO|RADEON_NEW_MEMMAP|RADEON_IS_IGP}, \
+ {0x1002, 0x964e, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_SUMO|RADEON_IS_MOBILITY|RADEON_NEW_MEMMAP|RADEON_IS_IGP},\
+ {0x1002, 0x964f, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_SUMO|RADEON_IS_MOBILITY|RADEON_NEW_MEMMAP|RADEON_IS_IGP},\
+ {0x1002, 0x9710, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_RS880|RADEON_NEW_MEMMAP|RADEON_IS_IGP}, \
+@@ -502,6 +510,8 @@
+ {0x1002, 0x9805, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_PALM|RADEON_NEW_MEMMAP|RADEON_IS_IGP}, \
+ {0x1002, 0x9806, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_PALM|RADEON_NEW_MEMMAP|RADEON_IS_IGP}, \
+ {0x1002, 0x9807, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_PALM|RADEON_NEW_MEMMAP|RADEON_IS_IGP}, \
++ {0x1002, 0x9808, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_PALM|RADEON_NEW_MEMMAP|RADEON_IS_IGP}, \
++ {0x1002, 0x9809, PCI_ANY_ID, PCI_ANY_ID, 0, 0, CHIP_PALM|RADEON_NEW_MEMMAP|RADEON_IS_IGP}, \
+ {0, 0, 0}
+
+ #define r128_PCI_IDS \
+diff --git a/include/linux/dcache.h b/include/linux/dcache.h
+index 62157c0..713c7c6 100644
+--- a/include/linux/dcache.h
++++ b/include/linux/dcache.h
+@@ -337,7 +337,8 @@ extern int d_validate(struct dentry *, struct dentry *);
+ */
+ extern char *dynamic_dname(struct dentry *, char *, int, const char *, ...);
+
+-extern char *__d_path(const struct path *path, struct path *root, char *, int);
++extern char *__d_path(const struct path *, const struct path *, char *, int);
++extern char *d_absolute_path(const struct path *, char *, int);
+ extern char *d_path(const struct path *, char *, int);
+ extern char *d_path_with_unreachable(const struct path *, char *, int);
+ extern char *dentry_path_raw(struct dentry *, char *, int);
+diff --git a/include/linux/fs.h b/include/linux/fs.h
+index 277f497..cf7bc25 100644
+--- a/include/linux/fs.h
++++ b/include/linux/fs.h
+@@ -1907,6 +1907,7 @@ extern int fd_statfs(int, struct kstatfs *);
+ extern int statfs_by_dentry(struct dentry *, struct kstatfs *);
+ extern int freeze_super(struct super_block *super);
+ extern int thaw_super(struct super_block *super);
++extern bool our_mnt(struct vfsmount *mnt);
+
+ extern int current_umask(void);
+
+diff --git a/include/linux/log2.h b/include/linux/log2.h
+index 25b8086..fd7ff3d 100644
+--- a/include/linux/log2.h
++++ b/include/linux/log2.h
+@@ -185,7 +185,6 @@ unsigned long __rounddown_pow_of_two(unsigned long n)
+ #define rounddown_pow_of_two(n) \
+ ( \
+ __builtin_constant_p(n) ? ( \
+- (n == 1) ? 0 : \
+ (1UL << ilog2(n))) : \
+ __rounddown_pow_of_two(n) \
+ )
+diff --git a/kernel/lockdep.c b/kernel/lockdep.c
+index 91d67ce..4479606 100644
+--- a/kernel/lockdep.c
++++ b/kernel/lockdep.c
+@@ -44,6 +44,7 @@
+ #include <linux/stringify.h>
+ #include <linux/bitops.h>
+ #include <linux/gfp.h>
++#include <linux/kmemcheck.h>
+
+ #include <asm/sections.h>
+
+@@ -2874,7 +2875,12 @@ static int mark_lock(struct task_struct *curr, struct held_lock *this,
+ void lockdep_init_map(struct lockdep_map *lock, const char *name,
+ struct lock_class_key *key, int subclass)
+ {
+- memset(lock, 0, sizeof(*lock));
++ int i;
++
++ kmemcheck_mark_initialized(lock, sizeof(*lock));
++
++ for (i = 0; i < NR_LOCKDEP_CACHING_CLASSES; i++)
++ lock->class_cache[i] = NULL;
+
+ #ifdef CONFIG_LOCK_STAT
+ lock->cpu = raw_smp_processor_id();
+diff --git a/kernel/time/alarmtimer.c b/kernel/time/alarmtimer.c
+index ea5e1a9..8b70c76 100644
+--- a/kernel/time/alarmtimer.c
++++ b/kernel/time/alarmtimer.c
+@@ -181,7 +181,7 @@ static enum hrtimer_restart alarmtimer_fired(struct hrtimer *timer)
+ struct alarm *alarm;
+ ktime_t expired = next->expires;
+
+- if (expired.tv64 >= now.tv64)
++ if (expired.tv64 > now.tv64)
+ break;
+
+ alarm = container_of(next, struct alarm, node);
+diff --git a/mm/hugetlb.c b/mm/hugetlb.c
+index bb28a5f..73f17c0 100644
+--- a/mm/hugetlb.c
++++ b/mm/hugetlb.c
+@@ -576,6 +576,7 @@ static void prep_compound_gigantic_page(struct page *page, unsigned long order)
+ __SetPageHead(page);
+ for (i = 1; i < nr_pages; i++, p = mem_map_next(p, page, i)) {
+ __SetPageTail(p);
++ set_page_count(p, 0);
+ p->first_page = page;
+ }
+ }
+diff --git a/mm/page_alloc.c b/mm/page_alloc.c
+index 6e8ecb6..e8fae15 100644
+--- a/mm/page_alloc.c
++++ b/mm/page_alloc.c
+@@ -355,8 +355,8 @@ void prep_compound_page(struct page *page, unsigned long order)
+ __SetPageHead(page);
+ for (i = 1; i < nr_pages; i++) {
+ struct page *p = page + i;
+-
+ __SetPageTail(p);
++ set_page_count(p, 0);
+ p->first_page = page;
+ }
+ }
+@@ -3370,9 +3370,15 @@ static void setup_zone_migrate_reserve(struct zone *zone)
+ unsigned long block_migratetype;
+ int reserve;
+
+- /* Get the start pfn, end pfn and the number of blocks to reserve */
++ /*
++ * Get the start pfn, end pfn and the number of blocks to reserve
++ * We have to be careful to be aligned to pageblock_nr_pages to
++ * make sure that we always check pfn_valid for the first page in
++ * the block.
++ */
+ start_pfn = zone->zone_start_pfn;
+ end_pfn = start_pfn + zone->spanned_pages;
++ start_pfn = roundup(start_pfn, pageblock_nr_pages);
+ reserve = roundup(min_wmark_pages(zone), pageblock_nr_pages) >>
+ pageblock_order;
+
+diff --git a/mm/percpu-vm.c b/mm/percpu-vm.c
+index ea53496..bfad724 100644
+--- a/mm/percpu-vm.c
++++ b/mm/percpu-vm.c
+@@ -143,8 +143,8 @@ static void pcpu_pre_unmap_flush(struct pcpu_chunk *chunk,
+ int page_start, int page_end)
+ {
+ flush_cache_vunmap(
+- pcpu_chunk_addr(chunk, pcpu_first_unit_cpu, page_start),
+- pcpu_chunk_addr(chunk, pcpu_last_unit_cpu, page_end));
++ pcpu_chunk_addr(chunk, pcpu_low_unit_cpu, page_start),
++ pcpu_chunk_addr(chunk, pcpu_high_unit_cpu, page_end));
+ }
+
+ static void __pcpu_unmap_pages(unsigned long addr, int nr_pages)
+@@ -206,8 +206,8 @@ static void pcpu_post_unmap_tlb_flush(struct pcpu_chunk *chunk,
+ int page_start, int page_end)
+ {
+ flush_tlb_kernel_range(
+- pcpu_chunk_addr(chunk, pcpu_first_unit_cpu, page_start),
+- pcpu_chunk_addr(chunk, pcpu_last_unit_cpu, page_end));
++ pcpu_chunk_addr(chunk, pcpu_low_unit_cpu, page_start),
++ pcpu_chunk_addr(chunk, pcpu_high_unit_cpu, page_end));
+ }
+
+ static int __pcpu_map_pages(unsigned long addr, struct page **pages,
+@@ -284,8 +284,8 @@ static void pcpu_post_map_flush(struct pcpu_chunk *chunk,
+ int page_start, int page_end)
+ {
+ flush_cache_vmap(
+- pcpu_chunk_addr(chunk, pcpu_first_unit_cpu, page_start),
+- pcpu_chunk_addr(chunk, pcpu_last_unit_cpu, page_end));
++ pcpu_chunk_addr(chunk, pcpu_low_unit_cpu, page_start),
++ pcpu_chunk_addr(chunk, pcpu_high_unit_cpu, page_end));
+ }
+
+ /**
+diff --git a/mm/percpu.c b/mm/percpu.c
+index bf80e55..93b5a7c 100644
+--- a/mm/percpu.c
++++ b/mm/percpu.c
+@@ -116,9 +116,9 @@ static int pcpu_atom_size __read_mostly;
+ static int pcpu_nr_slots __read_mostly;
+ static size_t pcpu_chunk_struct_size __read_mostly;
+
+-/* cpus with the lowest and highest unit numbers */
+-static unsigned int pcpu_first_unit_cpu __read_mostly;
+-static unsigned int pcpu_last_unit_cpu __read_mostly;
++/* cpus with the lowest and highest unit addresses */
++static unsigned int pcpu_low_unit_cpu __read_mostly;
++static unsigned int pcpu_high_unit_cpu __read_mostly;
+
+ /* the address of the first chunk which starts with the kernel static area */
+ void *pcpu_base_addr __read_mostly;
+@@ -984,19 +984,19 @@ phys_addr_t per_cpu_ptr_to_phys(void *addr)
+ {
+ void __percpu *base = __addr_to_pcpu_ptr(pcpu_base_addr);
+ bool in_first_chunk = false;
+- unsigned long first_start, first_end;
++ unsigned long first_low, first_high;
+ unsigned int cpu;
+
+ /*
+- * The following test on first_start/end isn't strictly
++ * The following test on unit_low/high isn't strictly
+ * necessary but will speed up lookups of addresses which
+ * aren't in the first chunk.
+ */
+- first_start = pcpu_chunk_addr(pcpu_first_chunk, pcpu_first_unit_cpu, 0);
+- first_end = pcpu_chunk_addr(pcpu_first_chunk, pcpu_last_unit_cpu,
+- pcpu_unit_pages);
+- if ((unsigned long)addr >= first_start &&
+- (unsigned long)addr < first_end) {
++ first_low = pcpu_chunk_addr(pcpu_first_chunk, pcpu_low_unit_cpu, 0);
++ first_high = pcpu_chunk_addr(pcpu_first_chunk, pcpu_high_unit_cpu,
++ pcpu_unit_pages);
++ if ((unsigned long)addr >= first_low &&
++ (unsigned long)addr < first_high) {
+ for_each_possible_cpu(cpu) {
+ void *start = per_cpu_ptr(base, cpu);
+
+@@ -1233,7 +1233,9 @@ int __init pcpu_setup_first_chunk(const struct pcpu_alloc_info *ai,
+
+ for (cpu = 0; cpu < nr_cpu_ids; cpu++)
+ unit_map[cpu] = UINT_MAX;
+- pcpu_first_unit_cpu = NR_CPUS;
++
++ pcpu_low_unit_cpu = NR_CPUS;
++ pcpu_high_unit_cpu = NR_CPUS;
+
+ for (group = 0, unit = 0; group < ai->nr_groups; group++, unit += i) {
+ const struct pcpu_group_info *gi = &ai->groups[group];
+@@ -1253,9 +1255,13 @@ int __init pcpu_setup_first_chunk(const struct pcpu_alloc_info *ai,
+ unit_map[cpu] = unit + i;
+ unit_off[cpu] = gi->base_offset + i * ai->unit_size;
+
+- if (pcpu_first_unit_cpu == NR_CPUS)
+- pcpu_first_unit_cpu = cpu;
+- pcpu_last_unit_cpu = cpu;
++ /* determine low/high unit_cpu */
++ if (pcpu_low_unit_cpu == NR_CPUS ||
++ unit_off[cpu] < unit_off[pcpu_low_unit_cpu])
++ pcpu_low_unit_cpu = cpu;
++ if (pcpu_high_unit_cpu == NR_CPUS ||
++ unit_off[cpu] > unit_off[pcpu_high_unit_cpu])
++ pcpu_high_unit_cpu = cpu;
+ }
+ }
+ pcpu_nr_units = unit;
+diff --git a/mm/vmalloc.c b/mm/vmalloc.c
+index 56faf31..3a65d6f7 100644
+--- a/mm/vmalloc.c
++++ b/mm/vmalloc.c
+@@ -1634,6 +1634,8 @@ void *__vmalloc_node_range(unsigned long size, unsigned long align,
+ return NULL;
+
+ addr = __vmalloc_area_node(area, gfp_mask, prot, node, caller);
++ if (!addr)
++ return NULL;
+
+ /*
+ * In this function, newly allocated vm_struct is not added
+diff --git a/security/apparmor/path.c b/security/apparmor/path.c
+index 36cc0cc..b566eba 100644
+--- a/security/apparmor/path.c
++++ b/security/apparmor/path.c
+@@ -57,23 +57,44 @@ static int prepend(char **buffer, int buflen, const char *str, int namelen)
+ static int d_namespace_path(struct path *path, char *buf, int buflen,
+ char **name, int flags)
+ {
+- struct path root, tmp;
+ char *res;
+- int connected, error = 0;
++ int error = 0;
++ int connected = 1;
++
++ if (path->mnt->mnt_flags & MNT_INTERNAL) {
++ /* it's not mounted anywhere */
++ res = dentry_path(path->dentry, buf, buflen);
++ *name = res;
++ if (IS_ERR(res)) {
++ *name = buf;
++ return PTR_ERR(res);
++ }
++ if (path->dentry->d_sb->s_magic == PROC_SUPER_MAGIC &&
++ strncmp(*name, "/sys/", 5) == 0) {
++ /* TODO: convert over to using a per namespace
++ * control instead of hard coded /proc
++ */
++ return prepend(name, *name - buf, "/proc", 5);
++ }
++ return 0;
++ }
+
+- /* Get the root we want to resolve too, released below */
++ /* resolve paths relative to chroot?*/
+ if (flags & PATH_CHROOT_REL) {
+- /* resolve paths relative to chroot */
++ struct path root;
+ get_fs_root(current->fs, &root);
+- } else {
+- /* resolve paths relative to namespace */
+- root.mnt = current->nsproxy->mnt_ns->root;
+- root.dentry = root.mnt->mnt_root;
+- path_get(&root);
++ res = __d_path(path, &root, buf, buflen);
++ if (res && !IS_ERR(res)) {
++ /* everything's fine */
++ *name = res;
++ path_put(&root);
++ goto ok;
++ }
++ path_put(&root);
++ connected = 0;
+ }
+
+- tmp = root;
+- res = __d_path(path, &tmp, buf, buflen);
++ res = d_absolute_path(path, buf, buflen);
+
+ *name = res;
+ /* handle error conditions - and still allow a partial path to
+@@ -84,7 +105,10 @@ static int d_namespace_path(struct path *path, char *buf, int buflen,
+ *name = buf;
+ goto out;
+ }
++ if (!our_mnt(path->mnt))
++ connected = 0;
+
++ok:
+ /* Handle two cases:
+ * 1. A deleted dentry && profile is not allowing mediation of deleted
+ * 2. On some filesystems, newly allocated dentries appear to the
+@@ -97,10 +121,7 @@ static int d_namespace_path(struct path *path, char *buf, int buflen,
+ goto out;
+ }
+
+- /* Determine if the path is connected to the expected root */
+- connected = tmp.dentry == root.dentry && tmp.mnt == root.mnt;
+-
+- /* If the path is not connected,
++ /* If the path is not connected to the expected root,
+ * check if it is a sysctl and handle specially else remove any
+ * leading / that __d_path may have returned.
+ * Unless
+@@ -112,17 +133,9 @@ static int d_namespace_path(struct path *path, char *buf, int buflen,
+ * namespace root.
+ */
+ if (!connected) {
+- /* is the disconnect path a sysctl? */
+- if (tmp.dentry->d_sb->s_magic == PROC_SUPER_MAGIC &&
+- strncmp(*name, "/sys/", 5) == 0) {
+- /* TODO: convert over to using a per namespace
+- * control instead of hard coded /proc
+- */
+- error = prepend(name, *name - buf, "/proc", 5);
+- } else if (!(flags & PATH_CONNECT_PATH) &&
++ if (!(flags & PATH_CONNECT_PATH) &&
+ !(((flags & CHROOT_NSCONNECT) == CHROOT_NSCONNECT) &&
+- (tmp.mnt == current->nsproxy->mnt_ns->root &&
+- tmp.dentry == tmp.mnt->mnt_root))) {
++ our_mnt(path->mnt))) {
+ /* disconnected path, don't return pathname starting
+ * with '/'
+ */
+@@ -133,8 +146,6 @@ static int d_namespace_path(struct path *path, char *buf, int buflen,
+ }
+
+ out:
+- path_put(&root);
+-
+ return error;
+ }
+
+diff --git a/security/tomoyo/realpath.c b/security/tomoyo/realpath.c
+index 6c601bd..d46922d 100644
+--- a/security/tomoyo/realpath.c
++++ b/security/tomoyo/realpath.c
+@@ -83,9 +83,8 @@ static char *tomoyo_get_absolute_path(struct path *path, char * const buffer,
+ {
+ char *pos = ERR_PTR(-ENOMEM);
+ if (buflen >= 256) {
+- struct path ns_root = { };
+ /* go to whatever namespace root we are under */
+- pos = __d_path(path, &ns_root, buffer, buflen - 1);
++ pos = d_absolute_path(path, buffer, buflen - 1);
+ if (!IS_ERR(pos) && *pos == '/' && pos[1]) {
+ struct inode *inode = path->dentry->d_inode;
+ if (inode && S_ISDIR(inode->i_mode)) {
+@@ -276,8 +275,16 @@ char *tomoyo_realpath_from_path(struct path *path)
+ pos = tomoyo_get_local_path(path->dentry, buf,
+ buf_len - 1);
+ /* Get absolute name for the rest. */
+- else
++ else {
+ pos = tomoyo_get_absolute_path(path, buf, buf_len - 1);
++ /*
++ * Fall back to local name if absolute name is not
++ * available.
++ */
++ if (pos == ERR_PTR(-EINVAL))
++ pos = tomoyo_get_local_path(path->dentry, buf,
++ buf_len - 1);
++ }
+ encode:
+ if (IS_ERR(pos))
+ continue;
+diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c
+index c687e14..20d92074 100644
+--- a/sound/pci/hda/patch_realtek.c
++++ b/sound/pci/hda/patch_realtek.c
+@@ -280,6 +280,8 @@ static int alc_mux_select(struct hda_codec *codec, unsigned int adc_idx,
+ imux = &spec->input_mux[mux_idx];
+ if (!imux->num_items && mux_idx > 0)
+ imux = &spec->input_mux[0];
++ if (!imux->num_items)
++ return 0;
+
+ if (idx >= imux->num_items)
+ idx = imux->num_items - 1;
+diff --git a/sound/pci/hda/patch_sigmatel.c b/sound/pci/hda/patch_sigmatel.c
+index 4538caa..5261fd8 100644
+--- a/sound/pci/hda/patch_sigmatel.c
++++ b/sound/pci/hda/patch_sigmatel.c
+@@ -214,6 +214,7 @@ struct sigmatel_spec {
+ unsigned int gpio_mute;
+ unsigned int gpio_led;
+ unsigned int gpio_led_polarity;
++ unsigned int vref_mute_led_nid; /* pin NID for mute-LED vref control */
+ unsigned int vref_led;
+
+ /* stream */
+@@ -4298,12 +4299,10 @@ static void stac_store_hints(struct hda_codec *codec)
+ spec->eapd_switch = val;
+ get_int_hint(codec, "gpio_led_polarity", &spec->gpio_led_polarity);
+ if (get_int_hint(codec, "gpio_led", &spec->gpio_led)) {
+- if (spec->gpio_led <= 8) {
+- spec->gpio_mask |= spec->gpio_led;
+- spec->gpio_dir |= spec->gpio_led;
+- if (spec->gpio_led_polarity)
+- spec->gpio_data |= spec->gpio_led;
+- }
++ spec->gpio_mask |= spec->gpio_led;
++ spec->gpio_dir |= spec->gpio_led;
++ if (spec->gpio_led_polarity)
++ spec->gpio_data |= spec->gpio_led;
+ }
+ }
+
+@@ -4893,8 +4892,14 @@ static int find_mute_led_gpio(struct hda_codec *codec, int default_polarity)
+ if (sscanf(dev->name, "HP_Mute_LED_%d_%x",
+ &spec->gpio_led_polarity,
+ &spec->gpio_led) == 2) {
+- if (spec->gpio_led < 4)
++ unsigned int max_gpio;
++ max_gpio = snd_hda_param_read(codec, codec->afg,
++ AC_PAR_GPIO_CAP);
++ max_gpio &= AC_GPIO_IO_COUNT;
++ if (spec->gpio_led < max_gpio)
+ spec->gpio_led = 1 << spec->gpio_led;
++ else
++ spec->vref_mute_led_nid = spec->gpio_led;
+ return 1;
+ }
+ if (sscanf(dev->name, "HP_Mute_LED_%d",
+@@ -5023,15 +5028,12 @@ static int stac92xx_pre_resume(struct hda_codec *codec)
+ struct sigmatel_spec *spec = codec->spec;
+
+ /* sync mute LED */
+- if (spec->gpio_led) {
+- if (spec->gpio_led <= 8) {
+- stac_gpio_set(codec, spec->gpio_mask,
+- spec->gpio_dir, spec->gpio_data);
+- } else {
+- stac_vrefout_set(codec,
+- spec->gpio_led, spec->vref_led);
+- }
+- }
++ if (spec->vref_mute_led_nid)
++ stac_vrefout_set(codec, spec->vref_mute_led_nid,
++ spec->vref_led);
++ else if (spec->gpio_led)
++ stac_gpio_set(codec, spec->gpio_mask,
++ spec->gpio_dir, spec->gpio_data);
+ return 0;
+ }
+
+@@ -5042,7 +5044,7 @@ static void stac92xx_set_power_state(struct hda_codec *codec, hda_nid_t fg,
+ struct sigmatel_spec *spec = codec->spec;
+
+ if (power_state == AC_PWRST_D3) {
+- if (spec->gpio_led > 8) {
++ if (spec->vref_mute_led_nid) {
+ /* with vref-out pin used for mute led control
+ * codec AFG is prevented from D3 state
+ */
+@@ -5095,7 +5097,7 @@ static int stac92xx_update_led_status(struct hda_codec *codec)
+ }
+ }
+ /*polarity defines *not* muted state level*/
+- if (spec->gpio_led <= 8) {
++ if (!spec->vref_mute_led_nid) {
+ if (muted)
+ spec->gpio_data &= ~spec->gpio_led; /* orange */
+ else
+@@ -5113,7 +5115,8 @@ static int stac92xx_update_led_status(struct hda_codec *codec)
+ muted_lvl = spec->gpio_led_polarity ?
+ AC_PINCTL_VREF_GRD : AC_PINCTL_VREF_HIZ;
+ spec->vref_led = muted ? muted_lvl : notmtd_lvl;
+- stac_vrefout_set(codec, spec->gpio_led, spec->vref_led);
++ stac_vrefout_set(codec, spec->vref_mute_led_nid,
++ spec->vref_led);
+ }
+ return 0;
+ }
+@@ -5634,7 +5637,7 @@ again:
+
+ #ifdef CONFIG_SND_HDA_POWER_SAVE
+ if (spec->gpio_led) {
+- if (spec->gpio_led <= 8) {
++ if (!spec->vref_mute_led_nid) {
+ spec->gpio_mask |= spec->gpio_led;
+ spec->gpio_dir |= spec->gpio_led;
+ spec->gpio_data |= spec->gpio_led;
+@@ -5955,7 +5958,7 @@ again:
+
+ #ifdef CONFIG_SND_HDA_POWER_SAVE
+ if (spec->gpio_led) {
+- if (spec->gpio_led <= 8) {
++ if (!spec->vref_mute_led_nid) {
+ spec->gpio_mask |= spec->gpio_led;
+ spec->gpio_dir |= spec->gpio_led;
+ spec->gpio_data |= spec->gpio_led;
+diff --git a/sound/pci/sis7019.c b/sound/pci/sis7019.c
+index bcf6152..fdc78ad 100644
+--- a/sound/pci/sis7019.c
++++ b/sound/pci/sis7019.c
+@@ -41,6 +41,7 @@ MODULE_SUPPORTED_DEVICE("{{SiS,SiS7019 Audio Accelerator}}");
+ static int index = SNDRV_DEFAULT_IDX1; /* Index 0-MAX */
+ static char *id = SNDRV_DEFAULT_STR1; /* ID for this card */
+ static int enable = 1;
++static int codecs = 1;
+
+ module_param(index, int, 0444);
+ MODULE_PARM_DESC(index, "Index value for SiS7019 Audio Accelerator.");
+@@ -48,6 +49,8 @@ module_param(id, charp, 0444);
+ MODULE_PARM_DESC(id, "ID string for SiS7019 Audio Accelerator.");
+ module_param(enable, bool, 0444);
+ MODULE_PARM_DESC(enable, "Enable SiS7019 Audio Accelerator.");
++module_param(codecs, int, 0444);
++MODULE_PARM_DESC(codecs, "Set bit to indicate that codec number is expected to be present (default 1)");
+
+ static DEFINE_PCI_DEVICE_TABLE(snd_sis7019_ids) = {
+ { PCI_DEVICE(PCI_VENDOR_ID_SI, 0x7019) },
+@@ -140,6 +143,9 @@ struct sis7019 {
+ dma_addr_t silence_dma_addr;
+ };
+
++/* These values are also used by the module param 'codecs' to indicate
++ * which codecs should be present.
++ */
+ #define SIS_PRIMARY_CODEC_PRESENT 0x0001
+ #define SIS_SECONDARY_CODEC_PRESENT 0x0002
+ #define SIS_TERTIARY_CODEC_PRESENT 0x0004
+@@ -1078,6 +1084,7 @@ static int sis_chip_init(struct sis7019 *sis)
+ {
+ unsigned long io = sis->ioport;
+ void __iomem *ioaddr = sis->ioaddr;
++ unsigned long timeout;
+ u16 status;
+ int count;
+ int i;
+@@ -1104,21 +1111,45 @@ static int sis_chip_init(struct sis7019 *sis)
+ while ((inw(io + SIS_AC97_STATUS) & SIS_AC97_STATUS_BUSY) && --count)
+ udelay(1);
+
++ /* Command complete, we can let go of the semaphore now.
++ */
++ outl(SIS_AC97_SEMA_RELEASE, io + SIS_AC97_SEMA);
++ if (!count)
++ return -EIO;
++
+ /* Now that we've finished the reset, find out what's attached.
++ * There are some codec/board combinations that take an extremely
++ * long time to come up. 350+ ms has been observed in the field,
++ * so we'll give them up to 500ms.
+ */
+- status = inl(io + SIS_AC97_STATUS);
+- if (status & SIS_AC97_STATUS_CODEC_READY)
+- sis->codecs_present |= SIS_PRIMARY_CODEC_PRESENT;
+- if (status & SIS_AC97_STATUS_CODEC2_READY)
+- sis->codecs_present |= SIS_SECONDARY_CODEC_PRESENT;
+- if (status & SIS_AC97_STATUS_CODEC3_READY)
+- sis->codecs_present |= SIS_TERTIARY_CODEC_PRESENT;
+-
+- /* All done, let go of the semaphore, and check for errors
++ sis->codecs_present = 0;
++ timeout = msecs_to_jiffies(500) + jiffies;
++ while (time_before_eq(jiffies, timeout)) {
++ status = inl(io + SIS_AC97_STATUS);
++ if (status & SIS_AC97_STATUS_CODEC_READY)
++ sis->codecs_present |= SIS_PRIMARY_CODEC_PRESENT;
++ if (status & SIS_AC97_STATUS_CODEC2_READY)
++ sis->codecs_present |= SIS_SECONDARY_CODEC_PRESENT;
++ if (status & SIS_AC97_STATUS_CODEC3_READY)
++ sis->codecs_present |= SIS_TERTIARY_CODEC_PRESENT;
++
++ if (sis->codecs_present == codecs)
++ break;
++
++ msleep(1);
++ }
++
++ /* All done, check for errors.
+ */
+- outl(SIS_AC97_SEMA_RELEASE, io + SIS_AC97_SEMA);
+- if (!sis->codecs_present || !count)
++ if (!sis->codecs_present) {
++ printk(KERN_ERR "sis7019: could not find any codecs\n");
+ return -EIO;
++ }
++
++ if (sis->codecs_present != codecs) {
++ printk(KERN_WARNING "sis7019: missing codecs, found %0x, expected %0x\n",
++ sis->codecs_present, codecs);
++ }
+
+ /* Let the hardware know that the audio driver is alive,
+ * and enable PCM slots on the AC-link for L/R playback (3 & 4) and
+@@ -1390,6 +1421,17 @@ static int __devinit snd_sis7019_probe(struct pci_dev *pci,
+ if (!enable)
+ goto error_out;
+
++ /* The user can specify which codecs should be present so that we
++ * can wait for them to show up if they are slow to recover from
++ * the AC97 cold reset. We default to a single codec, the primary.
++ *
++ * We assume that SIS_PRIMARY_*_PRESENT matches bits 0-2.
++ */
++ codecs &= SIS_PRIMARY_CODEC_PRESENT | SIS_SECONDARY_CODEC_PRESENT |
++ SIS_TERTIARY_CODEC_PRESENT;
++ if (!codecs)
++ codecs = SIS_PRIMARY_CODEC_PRESENT;
++
+ rc = snd_card_create(index, id, THIS_MODULE, sizeof(*sis), &card);
+ if (rc < 0)
+ goto error_out;
+diff --git a/sound/soc/soc-utils.c b/sound/soc/soc-utils.c
+index ec921ec..cd987de 100644
+--- a/sound/soc/soc-utils.c
++++ b/sound/soc/soc-utils.c
+@@ -57,7 +57,36 @@ int snd_soc_params_to_bclk(struct snd_pcm_hw_params *params)
+ }
+ EXPORT_SYMBOL_GPL(snd_soc_params_to_bclk);
+
+-static struct snd_soc_platform_driver dummy_platform;
++static const struct snd_pcm_hardware dummy_dma_hardware = {
++ .formats = 0xffffffff,
++ .channels_min = 1,
++ .channels_max = UINT_MAX,
++
++ /* Random values to keep userspace happy when checking constraints */
++ .info = SNDRV_PCM_INFO_INTERLEAVED |
++ SNDRV_PCM_INFO_BLOCK_TRANSFER,
++ .buffer_bytes_max = 128*1024,
++ .period_bytes_min = PAGE_SIZE,
++ .period_bytes_max = PAGE_SIZE*2,
++ .periods_min = 2,
++ .periods_max = 128,
++};
++
++static int dummy_dma_open(struct snd_pcm_substream *substream)
++{
++ snd_soc_set_runtime_hwparams(substream, &dummy_dma_hardware);
++
++ return 0;
++}
++
++static struct snd_pcm_ops dummy_dma_ops = {
++ .open = dummy_dma_open,
++ .ioctl = snd_pcm_lib_ioctl,
++};
++
++static struct snd_soc_platform_driver dummy_platform = {
++ .ops = &dummy_dma_ops,
++};
+
+ static __devinit int snd_soc_dummy_probe(struct platform_device *pdev)
+ {