Merge branch 'drm-fixes' of git://people.freedesktop.org/~airlied/linux
authorLinus Torvalds <torvalds@linux-foundation.org>
Sun, 14 Apr 2013 17:55:20 +0000 (10:55 -0700)
committerLinus Torvalds <torvalds@linux-foundation.org>
Sun, 14 Apr 2013 17:55:20 +0000 (10:55 -0700)
Pull drm fixes from Dave Airlie:
 "One fix for a hotplug locking regressions, and one fix for an oops if
  you unplug the monitor at an inopportune moment on the udl device."

* 'drm-fixes' of git://people.freedesktop.org/~airlied/linux:
  drm/fb-helper: Fix locking in drm_fb_helper_hotplug_event
  udl: handle EDID failure properly.

39 files changed:
Documentation/scsi/LICENSE.qla2xxx
MAINTAINERS
arch/m68k/include/asm/gpio.h
arch/x86/include/asm/tlb.h
arch/x86/mm/pgtable.c
drivers/scsi/ibmvscsi/ibmvscsi.c
drivers/scsi/ipr.c
drivers/scsi/libsas/sas_expander.c
drivers/scsi/lpfc/lpfc_sli.c
drivers/scsi/qla2xxx/qla_attr.c
drivers/scsi/qla2xxx/qla_dbg.c
drivers/scsi/qla2xxx/qla_def.h
drivers/scsi/qla2xxx/qla_gbl.h
drivers/scsi/qla2xxx/qla_init.c
drivers/scsi/qla2xxx/qla_mbx.c
drivers/scsi/qla2xxx/qla_version.h
drivers/scsi/st.c
drivers/target/target_core_alua.c
drivers/vhost/tcm_vhost.c
drivers/watchdog/Kconfig
fs/btrfs/tree-log.c
fs/cifs/connect.c
fs/inode.c
include/asm-generic/tlb.h
include/linux/capability.h
include/linux/ftrace.h
kernel/capability.c
kernel/trace/ftrace.c
kernel/trace/trace_stack.c
lib/kobject.c
mm/memory.c
sound/soc/codecs/wm5102.c
sound/soc/codecs/wm8903.c
sound/soc/samsung/i2s.c
sound/soc/soc-compress.c
sound/soc/soc-core.c
sound/soc/tegra/tegra_pcm.c
sound/usb/mixer_quirks.c
sound/usb/quirks.c

index 27a91cf..5020b7b 100644 (file)
@@ -1,4 +1,4 @@
-Copyright (c) 2003-2012 QLogic Corporation
+Copyright (c) 2003-2013 QLogic Corporation
 QLogic Linux FC-FCoE Driver
 
 This program includes a device driver for Linux 3.x.
index 61708c6..8bdd7a7 100644 (file)
@@ -6631,7 +6631,7 @@ S:        Supported
 F:     fs/reiserfs/
 
 REGISTER MAP ABSTRACTION
-M:     Mark Brown <broonie@opensource.wolfsonmicro.com>
+M:     Mark Brown <broonie@kernel.org>
 T:     git git://git.kernel.org/pub/scm/linux/kernel/git/broonie/regmap.git
 S:     Supported
 F:     drivers/base/regmap/
@@ -7379,7 +7379,7 @@ F:        sound/
 
 SOUND - SOC LAYER / DYNAMIC AUDIO POWER MANAGEMENT (ASoC)
 M:     Liam Girdwood <lgirdwood@gmail.com>
-M:     Mark Brown <broonie@opensource.wolfsonmicro.com>
+M:     Mark Brown <broonie@kernel.org>
 T:     git git://git.kernel.org/pub/scm/linux/kernel/git/broonie/sound.git
 L:     alsa-devel@alsa-project.org (moderated for non-subscribers)
 W:     http://alsa-project.org/main/index.php/ASoC
@@ -7468,7 +7468,7 @@ F:        drivers/clk/spear/
 
 SPI SUBSYSTEM
 M:     Grant Likely <grant.likely@secretlab.ca>
-M:     Mark Brown <broonie@opensource.wolfsonmicro.com>
+M:     Mark Brown <broonie@kernel.org>
 L:     spi-devel-general@lists.sourceforge.net
 Q:     http://patchwork.kernel.org/project/spi-devel-general/list/
 T:     git git://git.secretlab.ca/git/linux-2.6.git
@@ -8713,7 +8713,7 @@ F:        drivers/scsi/vmw_pvscsi.h
 
 VOLTAGE AND CURRENT REGULATOR FRAMEWORK
 M:     Liam Girdwood <lrg@ti.com>
-M:     Mark Brown <broonie@opensource.wolfsonmicro.com>
+M:     Mark Brown <broonie@kernel.org>
 W:     http://opensource.wolfsonmicro.com/node/15
 W:     http://www.slimlogic.co.uk/?p=48
 T:     git git://git.kernel.org/pub/scm/linux/kernel/git/lrg/regulator.git
index 4395ffc..8cc8343 100644 (file)
@@ -86,4 +86,24 @@ static inline int gpio_cansleep(unsigned gpio)
        return gpio < MCFGPIO_PIN_MAX ? 0 : __gpio_cansleep(gpio);
 }
 
+static inline int gpio_request_one(unsigned gpio, unsigned long flags, const char *label)
+{
+       int err;
+
+       err = gpio_request(gpio, label);
+       if (err)
+               return err;
+
+       if (flags & GPIOF_DIR_IN)
+               err = gpio_direction_input(gpio);
+       else
+               err = gpio_direction_output(gpio,
+                       (flags & GPIOF_INIT_HIGH) ? 1 : 0);
+
+       if (err)
+               gpio_free(gpio);
+
+       return err;
+}
+
 #endif
index 4fef207..c779730 100644 (file)
@@ -7,7 +7,7 @@
 
 #define tlb_flush(tlb)                                                 \
 {                                                                      \
-       if (tlb->fullmm == 0)                                           \
+       if (!tlb->fullmm && !tlb->need_flush_all)                       \
                flush_tlb_mm_range(tlb->mm, tlb->start, tlb->end, 0UL); \
        else                                                            \
                flush_tlb_mm_range(tlb->mm, 0UL, TLB_FLUSH_ALL, 0UL);   \
index 193350b..17fda6a 100644 (file)
@@ -58,6 +58,13 @@ void ___pte_free_tlb(struct mmu_gather *tlb, struct page *pte)
 void ___pmd_free_tlb(struct mmu_gather *tlb, pmd_t *pmd)
 {
        paravirt_release_pmd(__pa(pmd) >> PAGE_SHIFT);
+       /*
+        * NOTE! For PAE, any changes to the top page-directory-pointer-table
+        * entries need a full cr3 reload to flush.
+        */
+#ifdef CONFIG_X86_PAE
+       tlb->need_flush_all = 1;
+#endif
        tlb_remove_page(tlb, virt_to_page(pmd));
 }
 
index a044f59..d0fa4b6 100644 (file)
@@ -1899,8 +1899,8 @@ static int ibmvscsi_slave_configure(struct scsi_device *sdev)
                sdev->allow_restart = 1;
                blk_queue_rq_timeout(sdev->request_queue, 120 * HZ);
        }
-       scsi_adjust_queue_depth(sdev, 0, shost->cmd_per_lun);
        spin_unlock_irqrestore(shost->host_lock, lock_flags);
+       scsi_adjust_queue_depth(sdev, 0, shost->cmd_per_lun);
        return 0;
 }
 
index f328089..2197b57 100644 (file)
@@ -5148,7 +5148,7 @@ static int ipr_cancel_op(struct scsi_cmnd *scsi_cmd)
                ipr_trace;
        }
 
-       list_add_tail(&ipr_cmd->queue, &hrrq->hrrq_free_q);
+       list_add_tail(&ipr_cmd->queue, &ipr_cmd->hrrq->hrrq_free_q);
        if (!ipr_is_naca_model(res))
                res->needs_sync_complete = 1;
 
@@ -9349,7 +9349,10 @@ static int ipr_test_msi(struct ipr_ioa_cfg *ioa_cfg, struct pci_dev *pdev)
        int_reg = readl(ioa_cfg->regs.sense_interrupt_mask_reg);
        spin_unlock_irqrestore(ioa_cfg->host->host_lock, lock_flags);
 
-       rc = request_irq(pdev->irq, ipr_test_intr, 0, IPR_NAME, ioa_cfg);
+       if (ioa_cfg->intr_flag == IPR_USE_MSIX)
+               rc = request_irq(ioa_cfg->vectors_info[0].vec, ipr_test_intr, 0, IPR_NAME, ioa_cfg);
+       else
+               rc = request_irq(pdev->irq, ipr_test_intr, 0, IPR_NAME, ioa_cfg);
        if (rc) {
                dev_err(&pdev->dev, "Can not assign irq %d\n", pdev->irq);
                return rc;
@@ -9371,7 +9374,10 @@ static int ipr_test_msi(struct ipr_ioa_cfg *ioa_cfg, struct pci_dev *pdev)
 
        spin_unlock_irqrestore(ioa_cfg->host->host_lock, lock_flags);
 
-       free_irq(pdev->irq, ioa_cfg);
+       if (ioa_cfg->intr_flag == IPR_USE_MSIX)
+               free_irq(ioa_cfg->vectors_info[0].vec, ioa_cfg);
+       else
+               free_irq(pdev->irq, ioa_cfg);
 
        LEAVE;
 
@@ -9722,6 +9728,7 @@ static void __ipr_remove(struct pci_dev *pdev)
        spin_unlock_irqrestore(ioa_cfg->host->host_lock, host_lock_flags);
        wait_event(ioa_cfg->reset_wait_q, !ioa_cfg->in_reset_reload);
        flush_work(&ioa_cfg->work_q);
+       INIT_LIST_HEAD(&ioa_cfg->used_res_q);
        spin_lock_irqsave(ioa_cfg->host->host_lock, host_lock_flags);
 
        spin_lock(&ipr_driver_lock);
index aec2e0d..55cbd01 100644 (file)
@@ -235,6 +235,17 @@ static void sas_set_ex_phy(struct domain_device *dev, int phy_id, void *rsp)
        linkrate  = phy->linkrate;
        memcpy(sas_addr, phy->attached_sas_addr, SAS_ADDR_SIZE);
 
+       /* Handle vacant phy - rest of dr data is not valid so skip it */
+       if (phy->phy_state == PHY_VACANT) {
+               memset(phy->attached_sas_addr, 0, SAS_ADDR_SIZE);
+               phy->attached_dev_type = NO_DEVICE;
+               if (!test_bit(SAS_HA_ATA_EH_ACTIVE, &ha->state)) {
+                       phy->phy_id = phy_id;
+                       goto skip;
+               } else
+                       goto out;
+       }
+
        phy->attached_dev_type = to_dev_type(dr);
        if (test_bit(SAS_HA_ATA_EH_ACTIVE, &ha->state))
                goto out;
@@ -272,6 +283,7 @@ static void sas_set_ex_phy(struct domain_device *dev, int phy_id, void *rsp)
        phy->phy->maximum_linkrate = dr->pmax_linkrate;
        phy->phy->negotiated_linkrate = phy->linkrate;
 
+ skip:
        if (new_phy)
                if (sas_phy_add(phy->phy)) {
                        sas_phy_free(phy->phy);
@@ -388,7 +400,7 @@ int sas_ex_phy_discover(struct domain_device *dev, int single)
        if (!disc_req)
                return -ENOMEM;
 
-       disc_resp = alloc_smp_req(DISCOVER_RESP_SIZE);
+       disc_resp = alloc_smp_resp(DISCOVER_RESP_SIZE);
        if (!disc_resp) {
                kfree(disc_req);
                return -ENOMEM;
index 74b67d9..d43faf3 100644 (file)
@@ -438,11 +438,12 @@ lpfc_sli4_rq_put(struct lpfc_queue *hq, struct lpfc_queue *dq,
        struct lpfc_rqe *temp_hrqe;
        struct lpfc_rqe *temp_drqe;
        struct lpfc_register doorbell;
-       int put_index = hq->host_index;
+       int put_index;
 
        /* sanity check on queue memory */
        if (unlikely(!hq) || unlikely(!dq))
                return -ENOMEM;
+       put_index = hq->host_index;
        temp_hrqe = hq->qe[hq->host_index].rqe;
        temp_drqe = dq->qe[dq->host_index].rqe;
 
index 1d82eef..b3db9dc 100644 (file)
@@ -1938,11 +1938,6 @@ qla24xx_vport_delete(struct fc_vport *fc_vport)
                    "Timer for the VP[%d] has stopped\n", vha->vp_idx);
        }
 
-       /* No pending activities shall be there on the vha now */
-       if (ql2xextended_error_logging & ql_dbg_user)
-               msleep(random32()%10);  /* Just to see if something falls on
-                                       * the net we have placed below */
-
        BUG_ON(atomic_read(&vha->vref_count));
 
        qla2x00_free_fcports(vha);
index 1626de5..fbc305f 100644 (file)
@@ -15,6 +15,7 @@
  * | Mailbox commands             |       0x115b       | 0x111a-0x111b  |
  * |                              |                    | 0x112c-0x112e  |
  * |                              |                    | 0x113a         |
+ * |                              |                    | 0x1155-0x1158  |
  * | Device Discovery             |       0x2087       | 0x2020-0x2022, |
  * |                              |                    | 0x2016         |
  * | Queue Command and IO tracing |       0x3031       | 0x3006-0x300b  |
@@ -401,7 +402,7 @@ qla2xxx_copy_atioqueues(struct qla_hw_data *ha, void *ptr,
                void *ring;
        } aq, *aqp;
 
-       if (!ha->tgt.atio_q_length)
+       if (!ha->tgt.atio_ring)
                return ptr;
 
        num_queues = 1;
index c650991..65c5ff7 100644 (file)
@@ -863,7 +863,6 @@ typedef struct {
 #define        MBX_1           BIT_1
 #define        MBX_0           BIT_0
 
-#define RNID_TYPE_SET_VERSION  0x9
 #define RNID_TYPE_ASIC_TEMP    0xC
 
 /*
index eb3ca21..b310fa9 100644 (file)
@@ -358,9 +358,6 @@ extern int
 qla2x00_disable_fce_trace(scsi_qla_host_t *, uint64_t *, uint64_t *);
 
 extern int
-qla2x00_set_driver_version(scsi_qla_host_t *, char *);
-
-extern int
 qla2x00_read_sfp(scsi_qla_host_t *, dma_addr_t, uint8_t *,
        uint16_t, uint16_t, uint16_t, uint16_t);
 
index edf4d14..b592033 100644 (file)
@@ -619,8 +619,6 @@ qla2x00_initialize_adapter(scsi_qla_host_t *vha)
        if (IS_QLA24XX_TYPE(ha) || IS_QLA25XX(ha))
                qla24xx_read_fcp_prio_cfg(vha);
 
-       qla2x00_set_driver_version(vha, QLA2XXX_VERSION);
-
        return (rval);
 }
 
@@ -1399,7 +1397,7 @@ qla2x00_alloc_fw_dump(scsi_qla_host_t *vha)
                        mq_size += ha->max_rsp_queues *
                            (rsp->length * sizeof(response_t));
                }
-               if (ha->tgt.atio_q_length)
+               if (ha->tgt.atio_ring)
                        mq_size += ha->tgt.atio_q_length * sizeof(request_t);
                /* Allocate memory for Fibre Channel Event Buffer. */
                if (!IS_QLA25XX(ha) && !IS_QLA81XX(ha) && !IS_QLA83XX(ha))
index 186dd59..43345af 100644 (file)
@@ -3866,64 +3866,6 @@ qla81xx_restart_mpi_firmware(scsi_qla_host_t *vha)
        return rval;
 }
 
-int
-qla2x00_set_driver_version(scsi_qla_host_t *vha, char *version)
-{
-       int rval;
-       mbx_cmd_t mc;
-       mbx_cmd_t *mcp = &mc;
-       int len;
-       uint16_t dwlen;
-       uint8_t *str;
-       dma_addr_t str_dma;
-       struct qla_hw_data *ha = vha->hw;
-
-       if (!IS_FWI2_CAPABLE(ha) || IS_QLA82XX(ha))
-               return QLA_FUNCTION_FAILED;
-
-       ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1155,
-           "Entered %s.\n", __func__);
-
-       str = dma_pool_alloc(ha->s_dma_pool, GFP_KERNEL, &str_dma);
-       if (!str) {
-               ql_log(ql_log_warn, vha, 0x1156,
-                   "Failed to allocate driver version param.\n");
-               return QLA_MEMORY_ALLOC_FAILED;
-       }
-
-       memcpy(str, "\x7\x3\x11\x0", 4);
-       dwlen = str[0];
-       len = dwlen * sizeof(uint32_t) - 4;
-       memset(str + 4, 0, len);
-       if (len > strlen(version))
-               len = strlen(version);
-       memcpy(str + 4, version, len);
-
-       mcp->mb[0] = MBC_SET_RNID_PARAMS;
-       mcp->mb[1] = RNID_TYPE_SET_VERSION << 8 | dwlen;
-       mcp->mb[2] = MSW(LSD(str_dma));
-       mcp->mb[3] = LSW(LSD(str_dma));
-       mcp->mb[6] = MSW(MSD(str_dma));
-       mcp->mb[7] = LSW(MSD(str_dma));
-       mcp->out_mb = MBX_7|MBX_6|MBX_3|MBX_2|MBX_1|MBX_0;
-       mcp->in_mb = MBX_0;
-       mcp->tov = MBX_TOV_SECONDS;
-       mcp->flags = 0;
-       rval = qla2x00_mailbox_command(vha, mcp);
-
-       if (rval != QLA_SUCCESS) {
-               ql_dbg(ql_dbg_mbx, vha, 0x1157,
-                   "Failed=%x mb[0]=%x.\n", rval, mcp->mb[0]);
-       } else {
-               ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x1158,
-                   "Done %s.\n", __func__);
-       }
-
-       dma_pool_free(ha->s_dma_pool, str, str_dma);
-
-       return rval;
-}
-
 static int
 qla2x00_read_asic_temperature(scsi_qla_host_t *vha, uint16_t *temp)
 {
index 2b6e478..ec54036 100644 (file)
@@ -7,7 +7,7 @@
 /*
  * Driver version
  */
-#define QLA2XXX_VERSION      "8.04.00.08-k"
+#define QLA2XXX_VERSION      "8.04.00.13-k"
 
 #define QLA_DRIVER_MAJOR_VER   8
 #define QLA_DRIVER_MINOR_VER   4
index 8697447..2a32036 100644 (file)
@@ -4112,6 +4112,10 @@ static int st_probe(struct device *dev)
        tpnt->disk = disk;
        disk->private_data = &tpnt->driver;
        disk->queue = SDp->request_queue;
+       /* SCSI tape doesn't register this gendisk via add_disk().  Manually
+        * take queue reference that release_disk() expects. */
+       if (!blk_get_queue(disk->queue))
+               goto out_put_disk;
        tpnt->driver = &st_template;
 
        tpnt->device = SDp;
@@ -4185,7 +4189,7 @@ static int st_probe(struct device *dev)
        idr_preload_end();
        if (error < 0) {
                pr_warn("st: idr allocation failed: %d\n", error);
-               goto out_put_disk;
+               goto out_put_queue;
        }
        tpnt->index = error;
        sprintf(disk->disk_name, "st%d", tpnt->index);
@@ -4211,6 +4215,8 @@ out_remove_devs:
        spin_lock(&st_index_lock);
        idr_remove(&st_index_idr, tpnt->index);
        spin_unlock(&st_index_lock);
+out_put_queue:
+       blk_put_queue(disk->queue);
 out_put_disk:
        put_disk(disk);
        kfree(tpnt);
index ff1c5ee..cbe48ab 100644 (file)
@@ -409,6 +409,7 @@ static inline int core_alua_state_standby(
        case REPORT_LUNS:
        case RECEIVE_DIAGNOSTIC:
        case SEND_DIAGNOSTIC:
+               return 0;
        case MAINTENANCE_IN:
                switch (cdb[1] & 0x1f) {
                case MI_REPORT_TARGET_PGS:
@@ -451,6 +452,7 @@ static inline int core_alua_state_unavailable(
        switch (cdb[0]) {
        case INQUIRY:
        case REPORT_LUNS:
+               return 0;
        case MAINTENANCE_IN:
                switch (cdb[1] & 0x1f) {
                case MI_REPORT_TARGET_PGS:
@@ -491,6 +493,7 @@ static inline int core_alua_state_transition(
        switch (cdb[0]) {
        case INQUIRY:
        case REPORT_LUNS:
+               return 0;
        case MAINTENANCE_IN:
                switch (cdb[1] & 0x1f) {
                case MI_REPORT_TARGET_PGS:
index 2968b49..957a0b9 100644 (file)
@@ -74,9 +74,8 @@ enum {
 
 struct vhost_scsi {
        /* Protected by vhost_scsi->dev.mutex */
-       struct tcm_vhost_tpg *vs_tpg[VHOST_SCSI_MAX_TARGET];
+       struct tcm_vhost_tpg **vs_tpg;
        char vs_vhost_wwpn[TRANSPORT_IQN_LEN];
-       bool vs_endpoint;
 
        struct vhost_dev dev;
        struct vhost_virtqueue vqs[VHOST_SCSI_MAX_VQ];
@@ -579,9 +578,27 @@ static void tcm_vhost_submission_work(struct work_struct *work)
        }
 }
 
+static void vhost_scsi_send_bad_target(struct vhost_scsi *vs,
+       struct vhost_virtqueue *vq, int head, unsigned out)
+{
+       struct virtio_scsi_cmd_resp __user *resp;
+       struct virtio_scsi_cmd_resp rsp;
+       int ret;
+
+       memset(&rsp, 0, sizeof(rsp));
+       rsp.response = VIRTIO_SCSI_S_BAD_TARGET;
+       resp = vq->iov[out].iov_base;
+       ret = __copy_to_user(resp, &rsp, sizeof(rsp));
+       if (!ret)
+               vhost_add_used_and_signal(&vs->dev, vq, head, 0);
+       else
+               pr_err("Faulted on virtio_scsi_cmd_resp\n");
+}
+
 static void vhost_scsi_handle_vq(struct vhost_scsi *vs,
        struct vhost_virtqueue *vq)
 {
+       struct tcm_vhost_tpg **vs_tpg;
        struct virtio_scsi_cmd_req v_req;
        struct tcm_vhost_tpg *tv_tpg;
        struct tcm_vhost_cmd *tv_cmd;
@@ -590,8 +607,16 @@ static void vhost_scsi_handle_vq(struct vhost_scsi *vs,
        int head, ret;
        u8 target;
 
-       /* Must use ioctl VHOST_SCSI_SET_ENDPOINT */
-       if (unlikely(!vs->vs_endpoint))
+       /*
+        * We can handle the vq only after the endpoint is setup by calling the
+        * VHOST_SCSI_SET_ENDPOINT ioctl.
+        *
+        * TODO: Check that we are running from vhost_worker which acts
+        * as read-side critical section for vhost kind of RCU.
+        * See the comments in struct vhost_virtqueue in drivers/vhost/vhost.h
+        */
+       vs_tpg = rcu_dereference_check(vq->private_data, 1);
+       if (!vs_tpg)
                return;
 
        mutex_lock(&vq->mutex);
@@ -661,23 +686,11 @@ static void vhost_scsi_handle_vq(struct vhost_scsi *vs,
 
                /* Extract the tpgt */
                target = v_req.lun[1];
-               tv_tpg = vs->vs_tpg[target];
+               tv_tpg = ACCESS_ONCE(vs_tpg[target]);
 
                /* Target does not exist, fail the request */
                if (unlikely(!tv_tpg)) {
-                       struct virtio_scsi_cmd_resp __user *resp;
-                       struct virtio_scsi_cmd_resp rsp;
-
-                       memset(&rsp, 0, sizeof(rsp));
-                       rsp.response = VIRTIO_SCSI_S_BAD_TARGET;
-                       resp = vq->iov[out].iov_base;
-                       ret = __copy_to_user(resp, &rsp, sizeof(rsp));
-                       if (!ret)
-                               vhost_add_used_and_signal(&vs->dev,
-                                                         vq, head, 0);
-                       else
-                               pr_err("Faulted on virtio_scsi_cmd_resp\n");
-
+                       vhost_scsi_send_bad_target(vs, vq, head, out);
                        continue;
                }
 
@@ -690,22 +703,13 @@ static void vhost_scsi_handle_vq(struct vhost_scsi *vs,
                if (IS_ERR(tv_cmd)) {
                        vq_err(vq, "vhost_scsi_allocate_cmd failed %ld\n",
                                        PTR_ERR(tv_cmd));
-                       break;
+                       goto err_cmd;
                }
                pr_debug("Allocated tv_cmd: %p exp_data_len: %d, data_direction"
                        ": %d\n", tv_cmd, exp_data_len, data_direction);
 
                tv_cmd->tvc_vhost = vs;
                tv_cmd->tvc_vq = vq;
-
-               if (unlikely(vq->iov[out].iov_len !=
-                               sizeof(struct virtio_scsi_cmd_resp))) {
-                       vq_err(vq, "Expecting virtio_scsi_cmd_resp, got %zu"
-                               " bytes, out: %d, in: %d\n",
-                               vq->iov[out].iov_len, out, in);
-                       break;
-               }
-
                tv_cmd->tvc_resp = vq->iov[out].iov_base;
 
                /*
@@ -725,7 +729,7 @@ static void vhost_scsi_handle_vq(struct vhost_scsi *vs,
                                " exceeds SCSI_MAX_VARLEN_CDB_SIZE: %d\n",
                                scsi_command_size(tv_cmd->tvc_cdb),
                                TCM_VHOST_MAX_CDB_SIZE);
-                       break; /* TODO */
+                       goto err_free;
                }
                tv_cmd->tvc_lun = ((v_req.lun[2] << 8) | v_req.lun[3]) & 0x3FFF;
 
@@ -738,7 +742,7 @@ static void vhost_scsi_handle_vq(struct vhost_scsi *vs,
                                        data_direction == DMA_TO_DEVICE);
                        if (unlikely(ret)) {
                                vq_err(vq, "Failed to map iov to sgl\n");
-                               break; /* TODO */
+                               goto err_free;
                        }
                }
 
@@ -759,6 +763,13 @@ static void vhost_scsi_handle_vq(struct vhost_scsi *vs,
        }
 
        mutex_unlock(&vq->mutex);
+       return;
+
+err_free:
+       vhost_scsi_free_cmd(tv_cmd);
+err_cmd:
+       vhost_scsi_send_bad_target(vs, vq, head, out);
+       mutex_unlock(&vq->mutex);
 }
 
 static void vhost_scsi_ctl_handle_kick(struct vhost_work *work)
@@ -780,6 +791,20 @@ static void vhost_scsi_handle_kick(struct vhost_work *work)
        vhost_scsi_handle_vq(vs, vq);
 }
 
+static void vhost_scsi_flush_vq(struct vhost_scsi *vs, int index)
+{
+       vhost_poll_flush(&vs->dev.vqs[index].poll);
+}
+
+static void vhost_scsi_flush(struct vhost_scsi *vs)
+{
+       int i;
+
+       for (i = 0; i < VHOST_SCSI_MAX_VQ; i++)
+               vhost_scsi_flush_vq(vs, i);
+       vhost_work_flush(&vs->dev, &vs->vs_completion_work);
+}
+
 /*
  * Called from vhost_scsi_ioctl() context to walk the list of available
  * tcm_vhost_tpg with an active struct tcm_vhost_nexus
@@ -790,8 +815,10 @@ static int vhost_scsi_set_endpoint(
 {
        struct tcm_vhost_tport *tv_tport;
        struct tcm_vhost_tpg *tv_tpg;
+       struct tcm_vhost_tpg **vs_tpg;
+       struct vhost_virtqueue *vq;
+       int index, ret, i, len;
        bool match = false;
-       int index, ret;
 
        mutex_lock(&vs->dev.mutex);
        /* Verify that ring has been setup correctly. */
@@ -803,6 +830,15 @@ static int vhost_scsi_set_endpoint(
                }
        }
 
+       len = sizeof(vs_tpg[0]) * VHOST_SCSI_MAX_TARGET;
+       vs_tpg = kzalloc(len, GFP_KERNEL);
+       if (!vs_tpg) {
+               mutex_unlock(&vs->dev.mutex);
+               return -ENOMEM;
+       }
+       if (vs->vs_tpg)
+               memcpy(vs_tpg, vs->vs_tpg, len);
+
        mutex_lock(&tcm_vhost_mutex);
        list_for_each_entry(tv_tpg, &tcm_vhost_list, tv_tpg_list) {
                mutex_lock(&tv_tpg->tv_tpg_mutex);
@@ -817,14 +853,15 @@ static int vhost_scsi_set_endpoint(
                tv_tport = tv_tpg->tport;
 
                if (!strcmp(tv_tport->tport_name, t->vhost_wwpn)) {
-                       if (vs->vs_tpg[tv_tpg->tport_tpgt]) {
+                       if (vs->vs_tpg && vs->vs_tpg[tv_tpg->tport_tpgt]) {
                                mutex_unlock(&tv_tpg->tv_tpg_mutex);
                                mutex_unlock(&tcm_vhost_mutex);
                                mutex_unlock(&vs->dev.mutex);
+                               kfree(vs_tpg);
                                return -EEXIST;
                        }
                        tv_tpg->tv_tpg_vhost_count++;
-                       vs->vs_tpg[tv_tpg->tport_tpgt] = tv_tpg;
+                       vs_tpg[tv_tpg->tport_tpgt] = tv_tpg;
                        smp_mb__after_atomic_inc();
                        match = true;
                }
@@ -835,12 +872,27 @@ static int vhost_scsi_set_endpoint(
        if (match) {
                memcpy(vs->vs_vhost_wwpn, t->vhost_wwpn,
                       sizeof(vs->vs_vhost_wwpn));
-               vs->vs_endpoint = true;
+               for (i = 0; i < VHOST_SCSI_MAX_VQ; i++) {
+                       vq = &vs->vqs[i];
+                       /* Flushing the vhost_work acts as synchronize_rcu */
+                       mutex_lock(&vq->mutex);
+                       rcu_assign_pointer(vq->private_data, vs_tpg);
+                       vhost_init_used(vq);
+                       mutex_unlock(&vq->mutex);
+               }
                ret = 0;
        } else {
                ret = -EEXIST;
        }
 
+       /*
+        * Act as synchronize_rcu to make sure access to
+        * old vs->vs_tpg is finished.
+        */
+       vhost_scsi_flush(vs);
+       kfree(vs->vs_tpg);
+       vs->vs_tpg = vs_tpg;
+
        mutex_unlock(&vs->dev.mutex);
        return ret;
 }
@@ -851,6 +903,8 @@ static int vhost_scsi_clear_endpoint(
 {
        struct tcm_vhost_tport *tv_tport;
        struct tcm_vhost_tpg *tv_tpg;
+       struct vhost_virtqueue *vq;
+       bool match = false;
        int index, ret, i;
        u8 target;
 
@@ -862,9 +916,14 @@ static int vhost_scsi_clear_endpoint(
                        goto err_dev;
                }
        }
+
+       if (!vs->vs_tpg) {
+               mutex_unlock(&vs->dev.mutex);
+               return 0;
+       }
+
        for (i = 0; i < VHOST_SCSI_MAX_TARGET; i++) {
                target = i;
-
                tv_tpg = vs->vs_tpg[target];
                if (!tv_tpg)
                        continue;
@@ -886,10 +945,27 @@ static int vhost_scsi_clear_endpoint(
                }
                tv_tpg->tv_tpg_vhost_count--;
                vs->vs_tpg[target] = NULL;
-               vs->vs_endpoint = false;
+               match = true;
                mutex_unlock(&tv_tpg->tv_tpg_mutex);
        }
+       if (match) {
+               for (i = 0; i < VHOST_SCSI_MAX_VQ; i++) {
+                       vq = &vs->vqs[i];
+                       /* Flushing the vhost_work acts as synchronize_rcu */
+                       mutex_lock(&vq->mutex);
+                       rcu_assign_pointer(vq->private_data, NULL);
+                       mutex_unlock(&vq->mutex);
+               }
+       }
+       /*
+        * Act as synchronize_rcu to make sure access to
+        * old vs->vs_tpg is finished.
+        */
+       vhost_scsi_flush(vs);
+       kfree(vs->vs_tpg);
+       vs->vs_tpg = NULL;
        mutex_unlock(&vs->dev.mutex);
+
        return 0;
 
 err_tpg:
@@ -899,6 +975,24 @@ err_dev:
        return ret;
 }
 
+static int vhost_scsi_set_features(struct vhost_scsi *vs, u64 features)
+{
+       if (features & ~VHOST_SCSI_FEATURES)
+               return -EOPNOTSUPP;
+
+       mutex_lock(&vs->dev.mutex);
+       if ((features & (1 << VHOST_F_LOG_ALL)) &&
+           !vhost_log_access_ok(&vs->dev)) {
+               mutex_unlock(&vs->dev.mutex);
+               return -EFAULT;
+       }
+       vs->dev.acked_features = features;
+       smp_wmb();
+       vhost_scsi_flush(vs);
+       mutex_unlock(&vs->dev.mutex);
+       return 0;
+}
+
 static int vhost_scsi_open(struct inode *inode, struct file *f)
 {
        struct vhost_scsi *s;
@@ -939,38 +1033,6 @@ static int vhost_scsi_release(struct inode *inode, struct file *f)
        return 0;
 }
 
-static void vhost_scsi_flush_vq(struct vhost_scsi *vs, int index)
-{
-       vhost_poll_flush(&vs->dev.vqs[index].poll);
-}
-
-static void vhost_scsi_flush(struct vhost_scsi *vs)
-{
-       int i;
-
-       for (i = 0; i < VHOST_SCSI_MAX_VQ; i++)
-               vhost_scsi_flush_vq(vs, i);
-       vhost_work_flush(&vs->dev, &vs->vs_completion_work);
-}
-
-static int vhost_scsi_set_features(struct vhost_scsi *vs, u64 features)
-{
-       if (features & ~VHOST_SCSI_FEATURES)
-               return -EOPNOTSUPP;
-
-       mutex_lock(&vs->dev.mutex);
-       if ((features & (1 << VHOST_F_LOG_ALL)) &&
-           !vhost_log_access_ok(&vs->dev)) {
-               mutex_unlock(&vs->dev.mutex);
-               return -EFAULT;
-       }
-       vs->dev.acked_features = features;
-       smp_wmb();
-       vhost_scsi_flush(vs);
-       mutex_unlock(&vs->dev.mutex);
-       return 0;
-}
-
 static long vhost_scsi_ioctl(struct file *f, unsigned int ioctl,
                                unsigned long arg)
 {
index 9fcc70c..e89fc31 100644 (file)
@@ -117,7 +117,7 @@ config ARM_SP805_WATCHDOG
 
 config AT91RM9200_WATCHDOG
        tristate "AT91RM9200 watchdog"
-       depends on ARCH_AT91
+       depends on ARCH_AT91RM9200
        help
          Watchdog timer embedded into AT91RM9200 chips. This will reboot your
          system when the timeout is reached.
index 451fad9..ef96381 100644 (file)
@@ -317,6 +317,7 @@ static noinline int overwrite_item(struct btrfs_trans_handle *trans,
        unsigned long src_ptr;
        unsigned long dst_ptr;
        int overwrite_root = 0;
+       bool inode_item = key->type == BTRFS_INODE_ITEM_KEY;
 
        if (root->root_key.objectid != BTRFS_TREE_LOG_OBJECTID)
                overwrite_root = 1;
@@ -326,6 +327,9 @@ static noinline int overwrite_item(struct btrfs_trans_handle *trans,
 
        /* look for the key in the destination tree */
        ret = btrfs_search_slot(NULL, root, key, path, 0, 0);
+       if (ret < 0)
+               return ret;
+
        if (ret == 0) {
                char *src_copy;
                char *dst_copy;
@@ -367,6 +371,30 @@ static noinline int overwrite_item(struct btrfs_trans_handle *trans,
                        return 0;
                }
 
+               /*
+                * We need to load the old nbytes into the inode so when we
+                * replay the extents we've logged we get the right nbytes.
+                */
+               if (inode_item) {
+                       struct btrfs_inode_item *item;
+                       u64 nbytes;
+
+                       item = btrfs_item_ptr(path->nodes[0], path->slots[0],
+                                             struct btrfs_inode_item);
+                       nbytes = btrfs_inode_nbytes(path->nodes[0], item);
+                       item = btrfs_item_ptr(eb, slot,
+                                             struct btrfs_inode_item);
+                       btrfs_set_inode_nbytes(eb, item, nbytes);
+               }
+       } else if (inode_item) {
+               struct btrfs_inode_item *item;
+
+               /*
+                * New inode, set nbytes to 0 so that the nbytes comes out
+                * properly when we replay the extents.
+                */
+               item = btrfs_item_ptr(eb, slot, struct btrfs_inode_item);
+               btrfs_set_inode_nbytes(eb, item, 0);
        }
 insert:
        btrfs_release_path(path);
@@ -486,7 +514,7 @@ static noinline int replay_one_extent(struct btrfs_trans_handle *trans,
        int found_type;
        u64 extent_end;
        u64 start = key->offset;
-       u64 saved_nbytes;
+       u64 nbytes = 0;
        struct btrfs_file_extent_item *item;
        struct inode *inode = NULL;
        unsigned long size;
@@ -496,10 +524,19 @@ static noinline int replay_one_extent(struct btrfs_trans_handle *trans,
        found_type = btrfs_file_extent_type(eb, item);
 
        if (found_type == BTRFS_FILE_EXTENT_REG ||
-           found_type == BTRFS_FILE_EXTENT_PREALLOC)
-               extent_end = start + btrfs_file_extent_num_bytes(eb, item);
-       else if (found_type == BTRFS_FILE_EXTENT_INLINE) {
+           found_type == BTRFS_FILE_EXTENT_PREALLOC) {
+               nbytes = btrfs_file_extent_num_bytes(eb, item);
+               extent_end = start + nbytes;
+
+               /*
+                * We don't add to the inodes nbytes if we are prealloc or a
+                * hole.
+                */
+               if (btrfs_file_extent_disk_bytenr(eb, item) == 0)
+                       nbytes = 0;
+       } else if (found_type == BTRFS_FILE_EXTENT_INLINE) {
                size = btrfs_file_extent_inline_len(eb, item);
+               nbytes = btrfs_file_extent_ram_bytes(eb, item);
                extent_end = ALIGN(start + size, root->sectorsize);
        } else {
                ret = 0;
@@ -548,7 +585,6 @@ static noinline int replay_one_extent(struct btrfs_trans_handle *trans,
        }
        btrfs_release_path(path);
 
-       saved_nbytes = inode_get_bytes(inode);
        /* drop any overlapping extents */
        ret = btrfs_drop_extents(trans, root, inode, start, extent_end, 1);
        BUG_ON(ret);
@@ -635,7 +671,7 @@ static noinline int replay_one_extent(struct btrfs_trans_handle *trans,
                BUG_ON(ret);
        }
 
-       inode_set_bytes(inode, saved_nbytes);
+       inode_add_bytes(inode, nbytes);
        ret = btrfs_update_inode(trans, root, inode);
 out:
        if (inode)
index 991c63c..21b3a29 100644 (file)
@@ -1575,14 +1575,24 @@ cifs_parse_mount_options(const char *mountdata, const char *devname,
                        }
                        break;
                case Opt_blank_pass:
-                       vol->password = NULL;
-                       break;
-               case Opt_pass:
                        /* passwords have to be handled differently
                         * to allow the character used for deliminator
                         * to be passed within them
                         */
 
+                       /*
+                        * Check if this is a case where the  password
+                        * starts with a delimiter
+                        */
+                       tmp_end = strchr(data, '=');
+                       tmp_end++;
+                       if (!(tmp_end < end && tmp_end[1] == delim)) {
+                               /* No it is not. Set the password to NULL */
+                               vol->password = NULL;
+                               break;
+                       }
+                       /* Yes it is. Drop down to Opt_pass below.*/
+               case Opt_pass:
                        /* Obtain the value string */
                        value = strchr(data, '=');
                        value++;
index f5f7c06..a898b3d 100644 (file)
@@ -725,7 +725,7 @@ void prune_icache_sb(struct super_block *sb, int nr_to_scan)
                 * inode to the back of the list so we don't spin on it.
                 */
                if (!spin_trylock(&inode->i_lock)) {
-                       list_move_tail(&inode->i_lru, &sb->s_inode_lru);
+                       list_move(&inode->i_lru, &sb->s_inode_lru);
                        continue;
                }
 
index 25f01d0..b1b1fa6 100644 (file)
@@ -99,7 +99,12 @@ struct mmu_gather {
        unsigned int            need_flush : 1, /* Did free PTEs */
                                fast_mode  : 1; /* No batching   */
 
-       unsigned int            fullmm;
+       /* we are in the middle of an operation to clear
+        * a full mm and can make some optimizations */
+       unsigned int            fullmm : 1,
+       /* we have performed an operation which
+        * requires a complete flush of the tlb */
+                               need_flush_all : 1;
 
        struct mmu_gather_batch *active;
        struct mmu_gather_batch local;
index 98503b7..d9a4f7f 100644 (file)
@@ -35,6 +35,7 @@ struct cpu_vfs_cap_data {
 #define _KERNEL_CAP_T_SIZE     (sizeof(kernel_cap_t))
 
 
+struct file;
 struct inode;
 struct dentry;
 struct user_namespace;
@@ -211,6 +212,7 @@ extern bool capable(int cap);
 extern bool ns_capable(struct user_namespace *ns, int cap);
 extern bool nsown_capable(int cap);
 extern bool inode_capable(const struct inode *inode, int cap);
+extern bool file_ns_capable(const struct file *file, struct user_namespace *ns, int cap);
 
 /* audit system wants to get cap info from files as well */
 extern int get_vfs_caps_from_disk(const struct dentry *dentry, struct cpu_vfs_cap_data *cpu_caps);
index 167abf9..52da2a2 100644 (file)
@@ -396,7 +396,6 @@ ssize_t ftrace_filter_write(struct file *file, const char __user *ubuf,
                            size_t cnt, loff_t *ppos);
 ssize_t ftrace_notrace_write(struct file *file, const char __user *ubuf,
                             size_t cnt, loff_t *ppos);
-loff_t ftrace_regex_lseek(struct file *file, loff_t offset, int whence);
 int ftrace_regex_release(struct inode *inode, struct file *file);
 
 void __init
@@ -569,6 +568,8 @@ static inline int
 ftrace_regex_release(struct inode *inode, struct file *file) { return -ENODEV; }
 #endif /* CONFIG_DYNAMIC_FTRACE */
 
+loff_t ftrace_filter_lseek(struct file *file, loff_t offset, int whence);
+
 /* totally disable ftrace - can not re-enable after this */
 void ftrace_kill(void);
 
index 493d972..f6c2ce5 100644 (file)
@@ -393,6 +393,30 @@ bool ns_capable(struct user_namespace *ns, int cap)
 EXPORT_SYMBOL(ns_capable);
 
 /**
+ * file_ns_capable - Determine if the file's opener had a capability in effect
+ * @file:  The file we want to check
+ * @ns:  The usernamespace we want the capability in
+ * @cap: The capability to be tested for
+ *
+ * Return true if task that opened the file had a capability in effect
+ * when the file was opened.
+ *
+ * This does not set PF_SUPERPRIV because the caller may not
+ * actually be privileged.
+ */
+bool file_ns_capable(const struct file *file, struct user_namespace *ns, int cap)
+{
+       if (WARN_ON_ONCE(!cap_valid(cap)))
+               return false;
+
+       if (security_capable(file->f_cred, ns, cap) == 0)
+               return true;
+
+       return false;
+}
+EXPORT_SYMBOL(file_ns_capable);
+
+/**
  * capable - Determine if the current task has a superior capability in effect
  * @cap: The capability to be tested for
  *
index 926ebfb..2461ede 100644 (file)
@@ -1052,6 +1052,19 @@ static __init void ftrace_profile_debugfs(struct dentry *d_tracer)
 
 static struct pid * const ftrace_swapper_pid = &init_struct_pid;
 
+loff_t
+ftrace_filter_lseek(struct file *file, loff_t offset, int whence)
+{
+       loff_t ret;
+
+       if (file->f_mode & FMODE_READ)
+               ret = seq_lseek(file, offset, whence);
+       else
+               file->f_pos = ret = 1;
+
+       return ret;
+}
+
 #ifdef CONFIG_DYNAMIC_FTRACE
 
 #ifndef CONFIG_FTRACE_MCOUNT_RECORD
@@ -2612,7 +2625,7 @@ static void ftrace_filter_reset(struct ftrace_hash *hash)
  * routine, you can use ftrace_filter_write() for the write
  * routine if @flag has FTRACE_ITER_FILTER set, or
  * ftrace_notrace_write() if @flag has FTRACE_ITER_NOTRACE set.
- * ftrace_regex_lseek() should be used as the lseek routine, and
+ * ftrace_filter_lseek() should be used as the lseek routine, and
  * release must call ftrace_regex_release().
  */
 int
@@ -2696,19 +2709,6 @@ ftrace_notrace_open(struct inode *inode, struct file *file)
                                 inode, file);
 }
 
-loff_t
-ftrace_regex_lseek(struct file *file, loff_t offset, int whence)
-{
-       loff_t ret;
-
-       if (file->f_mode & FMODE_READ)
-               ret = seq_lseek(file, offset, whence);
-       else
-               file->f_pos = ret = 1;
-
-       return ret;
-}
-
 static int ftrace_match(char *str, char *regex, int len, int type)
 {
        int matched = 0;
@@ -3570,7 +3570,7 @@ static const struct file_operations ftrace_filter_fops = {
        .open = ftrace_filter_open,
        .read = seq_read,
        .write = ftrace_filter_write,
-       .llseek = ftrace_regex_lseek,
+       .llseek = ftrace_filter_lseek,
        .release = ftrace_regex_release,
 };
 
@@ -3578,7 +3578,7 @@ static const struct file_operations ftrace_notrace_fops = {
        .open = ftrace_notrace_open,
        .read = seq_read,
        .write = ftrace_notrace_write,
-       .llseek = ftrace_regex_lseek,
+       .llseek = ftrace_filter_lseek,
        .release = ftrace_regex_release,
 };
 
@@ -3783,8 +3783,8 @@ static const struct file_operations ftrace_graph_fops = {
        .open           = ftrace_graph_open,
        .read           = seq_read,
        .write          = ftrace_graph_write,
+       .llseek         = ftrace_filter_lseek,
        .release        = ftrace_graph_release,
-       .llseek         = seq_lseek,
 };
 #endif /* CONFIG_FUNCTION_GRAPH_TRACER */
 
@@ -4439,7 +4439,7 @@ static const struct file_operations ftrace_pid_fops = {
        .open           = ftrace_pid_open,
        .write          = ftrace_pid_write,
        .read           = seq_read,
-       .llseek         = seq_lseek,
+       .llseek         = ftrace_filter_lseek,
        .release        = ftrace_pid_release,
 };
 
index 42ca822..83a8b5b 100644 (file)
@@ -322,7 +322,7 @@ static const struct file_operations stack_trace_filter_fops = {
        .open = stack_trace_filter_open,
        .read = seq_read,
        .write = ftrace_filter_write,
-       .llseek = ftrace_regex_lseek,
+       .llseek = ftrace_filter_lseek,
        .release = ftrace_regex_release,
 };
 
index e07ee1f..a654866 100644 (file)
@@ -529,6 +529,13 @@ struct kobject *kobject_get(struct kobject *kobj)
        return kobj;
 }
 
+static struct kobject *kobject_get_unless_zero(struct kobject *kobj)
+{
+       if (!kref_get_unless_zero(&kobj->kref))
+               kobj = NULL;
+       return kobj;
+}
+
 /*
  * kobject_cleanup - free kobject resources.
  * @kobj: object to cleanup
@@ -751,7 +758,7 @@ struct kobject *kset_find_obj(struct kset *kset, const char *name)
 
        list_for_each_entry(k, &kset->list, entry) {
                if (kobject_name(k) && !strcmp(kobject_name(k), name)) {
-                       ret = kobject_get(k);
+                       ret = kobject_get_unless_zero(k);
                        break;
                }
        }
index 494526a..13cbc42 100644 (file)
@@ -216,6 +216,7 @@ void tlb_gather_mmu(struct mmu_gather *tlb, struct mm_struct *mm, bool fullmm)
        tlb->mm = mm;
 
        tlb->fullmm     = fullmm;
+       tlb->need_flush_all = 0;
        tlb->start      = -1UL;
        tlb->end        = 0;
        tlb->need_flush = 0;
index b82bbf5..34d0201 100644 (file)
@@ -584,7 +584,7 @@ static int wm5102_sysclk_ev(struct snd_soc_dapm_widget *w,
                            struct snd_kcontrol *kcontrol, int event)
 {
        struct snd_soc_codec *codec = w->codec;
-       struct arizona *arizona = dev_get_drvdata(codec->dev);
+       struct arizona *arizona = dev_get_drvdata(codec->dev->parent);
        struct regmap *regmap = codec->control_data;
        const struct reg_default *patch = NULL;
        int i, patch_size;
index 134e41c..f8a31ad 100644 (file)
@@ -1083,6 +1083,8 @@ static const struct snd_soc_dapm_route wm8903_intercon[] = {
        { "ROP", NULL, "Right Speaker PGA" },
        { "RON", NULL, "Right Speaker PGA" },
 
+       { "Charge Pump", NULL, "CLK_DSP" },
+
        { "Left Headphone Output PGA", NULL, "Charge Pump" },
        { "Right Headphone Output PGA", NULL, "Charge Pump" },
        { "Left Line Output PGA", NULL, "Charge Pump" },
index d7231e3..6bbeb0b 100644 (file)
@@ -972,6 +972,7 @@ static const struct snd_soc_dai_ops samsung_i2s_dai_ops = {
 static struct i2s_dai *i2s_alloc_dai(struct platform_device *pdev, bool sec)
 {
        struct i2s_dai *i2s;
+       int ret;
 
        i2s = devm_kzalloc(&pdev->dev, sizeof(struct i2s_dai), GFP_KERNEL);
        if (i2s == NULL)
@@ -996,15 +997,17 @@ static struct i2s_dai *i2s_alloc_dai(struct platform_device *pdev, bool sec)
                i2s->i2s_dai_drv.capture.channels_max = 2;
                i2s->i2s_dai_drv.capture.rates = SAMSUNG_I2S_RATES;
                i2s->i2s_dai_drv.capture.formats = SAMSUNG_I2S_FMTS;
+               dev_set_drvdata(&i2s->pdev->dev, i2s);
        } else {        /* Create a new platform_device for Secondary */
-               i2s->pdev = platform_device_register_resndata(NULL,
-                               "samsung-i2s-sec", -1, NULL, 0, NULL, 0);
+               i2s->pdev = platform_device_alloc("samsung-i2s-sec", -1);
                if (IS_ERR(i2s->pdev))
                        return NULL;
-       }
 
-       /* Pre-assign snd_soc_dai_set_drvdata */
-       dev_set_drvdata(&i2s->pdev->dev, i2s);
+               platform_set_drvdata(i2s->pdev, i2s);
+               ret = platform_device_add(i2s->pdev);
+               if (ret < 0)
+                       return NULL;
+       }
 
        return i2s;
 }
@@ -1107,6 +1110,10 @@ static int samsung_i2s_probe(struct platform_device *pdev)
 
        if (samsung_dai_type == TYPE_SEC) {
                sec_dai = dev_get_drvdata(&pdev->dev);
+               if (!sec_dai) {
+                       dev_err(&pdev->dev, "Unable to get drvdata\n");
+                       return -EFAULT;
+               }
                snd_soc_register_dai(&sec_dai->pdev->dev,
                        &sec_dai->i2s_dai_drv);
                asoc_dma_platform_register(&pdev->dev);
index b5b3db7..ed0bfb0 100644 (file)
@@ -211,19 +211,27 @@ static int soc_compr_set_params(struct snd_compr_stream *cstream,
        if (platform->driver->compr_ops && platform->driver->compr_ops->set_params) {
                ret = platform->driver->compr_ops->set_params(cstream, params);
                if (ret < 0)
-                       goto out;
+                       goto err;
        }
 
        if (rtd->dai_link->compr_ops && rtd->dai_link->compr_ops->set_params) {
                ret = rtd->dai_link->compr_ops->set_params(cstream);
                if (ret < 0)
-                       goto out;
+                       goto err;
        }
 
        snd_soc_dapm_stream_event(rtd, SNDRV_PCM_STREAM_PLAYBACK,
                                SND_SOC_DAPM_STREAM_START);
 
-out:
+       /* cancel any delayed stream shutdown that is pending */
+       rtd->pop_wait = 0;
+       mutex_unlock(&rtd->pcm_mutex);
+
+       cancel_delayed_work_sync(&rtd->delayed_work);
+
+       return ret;
+
+err:
        mutex_unlock(&rtd->pcm_mutex);
        return ret;
 }
index 507d251..ff4b45a 100644 (file)
@@ -2963,7 +2963,7 @@ int snd_soc_put_volsw_range(struct snd_kcontrol *kcontrol,
        val = val << shift;
 
        ret = snd_soc_update_bits_locked(codec, reg, val_mask, val);
-       if (ret != 0)
+       if (ret < 0)
                return ret;
 
        if (snd_soc_volsw_is_stereo(mc)) {
index c925ab0..5e2c55c 100644 (file)
@@ -43,8 +43,6 @@
 static const struct snd_pcm_hardware tegra_pcm_hardware = {
        .info                   = SNDRV_PCM_INFO_MMAP |
                                  SNDRV_PCM_INFO_MMAP_VALID |
-                                 SNDRV_PCM_INFO_PAUSE |
-                                 SNDRV_PCM_INFO_RESUME |
                                  SNDRV_PCM_INFO_INTERLEAVED,
        .formats                = SNDRV_PCM_FMTBIT_S16_LE,
        .channels_min           = 2,
@@ -127,26 +125,6 @@ static int tegra_pcm_hw_free(struct snd_pcm_substream *substream)
        return 0;
 }
 
-static int tegra_pcm_trigger(struct snd_pcm_substream *substream, int cmd)
-{
-       switch (cmd) {
-       case SNDRV_PCM_TRIGGER_START:
-       case SNDRV_PCM_TRIGGER_RESUME:
-       case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
-               return snd_dmaengine_pcm_trigger(substream,
-                                       SNDRV_PCM_TRIGGER_START);
-
-       case SNDRV_PCM_TRIGGER_STOP:
-       case SNDRV_PCM_TRIGGER_SUSPEND:
-       case SNDRV_PCM_TRIGGER_PAUSE_PUSH:
-               return snd_dmaengine_pcm_trigger(substream,
-                                       SNDRV_PCM_TRIGGER_STOP);
-       default:
-               return -EINVAL;
-       }
-       return 0;
-}
-
 static int tegra_pcm_mmap(struct snd_pcm_substream *substream,
                                struct vm_area_struct *vma)
 {
@@ -164,7 +142,7 @@ static struct snd_pcm_ops tegra_pcm_ops = {
        .ioctl          = snd_pcm_lib_ioctl,
        .hw_params      = tegra_pcm_hw_params,
        .hw_free        = tegra_pcm_hw_free,
-       .trigger        = tegra_pcm_trigger,
+       .trigger        = snd_dmaengine_pcm_trigger,
        .pointer        = snd_dmaengine_pcm_pointer,
        .mmap           = tegra_pcm_mmap,
 };
index 497d274..ebe9144 100644 (file)
@@ -509,7 +509,7 @@ static int snd_nativeinstruments_control_get(struct snd_kcontrol *kcontrol,
        else
                ret = usb_control_msg(dev, usb_rcvctrlpipe(dev, 0), bRequest,
                                  USB_TYPE_VENDOR | USB_RECIP_DEVICE | USB_DIR_IN,
-                                 0, cpu_to_le16(wIndex),
+                                 0, wIndex,
                                  &tmp, sizeof(tmp), 1000);
        up_read(&mixer->chip->shutdown_rwsem);
 
@@ -540,7 +540,7 @@ static int snd_nativeinstruments_control_put(struct snd_kcontrol *kcontrol,
        else
                ret = usb_control_msg(dev, usb_sndctrlpipe(dev, 0), bRequest,
                                  USB_TYPE_VENDOR | USB_RECIP_DEVICE | USB_DIR_OUT,
-                                 cpu_to_le16(wValue), cpu_to_le16(wIndex),
+                                 wValue, wIndex,
                                  NULL, 0, 1000);
        up_read(&mixer->chip->shutdown_rwsem);
 
index 5325a38..9c5ab22 100644 (file)
@@ -486,7 +486,7 @@ static int snd_usb_nativeinstruments_boot_quirk(struct usb_device *dev)
 {
        int ret = usb_control_msg(dev, usb_sndctrlpipe(dev, 0),
                                  0xaf, USB_TYPE_VENDOR | USB_RECIP_DEVICE,
-                                 cpu_to_le16(1), 0, NULL, 0, 1000);
+                                 1, 0, NULL, 0, 1000);
 
        if (ret < 0)
                return ret;