diff options
| author | Srinivasarao P <spathi@codeaurora.org> | 2018-08-16 10:31:30 +0530 |
|---|---|---|
| committer | Srinivasarao P <spathi@codeaurora.org> | 2018-08-24 00:07:01 +0530 |
| commit | 79de04d8065db03fb4a0cf9d2bf1916b092cabcc (patch) | |
| tree | 54733763f20f975ad1b37d26d56690012c0b6786 /drivers/char/tpm/tpm-dev.c | |
| parent | 4bef50d041e80243d279ed1bccda5297b81ba306 (diff) | |
| parent | f057ff937754efc42d56bee825187b2ce6c36958 (diff) | |
Merge android-4.4.148 (f057ff9) into msm-4.4
* refs/heads/tmp-f057ff9
Linux 4.4.148
x86/speculation/l1tf: Unbreak !__HAVE_ARCH_PFN_MODIFY_ALLOWED architectures
x86/init: fix build with CONFIG_SWAP=n
x86/speculation/l1tf: Fix up CPU feature flags
x86/mm/kmmio: Make the tracer robust against L1TF
x86/mm/pat: Make set_memory_np() L1TF safe
x86/speculation/l1tf: Make pmd/pud_mknotpresent() invert
x86/speculation/l1tf: Invert all not present mappings
x86/speculation/l1tf: Fix up pte->pfn conversion for PAE
x86/speculation/l1tf: Protect PAE swap entries against L1TF
x86/cpufeatures: Add detection of L1D cache flush support.
x86/speculation/l1tf: Extend 64bit swap file size limit
x86/bugs: Move the l1tf function and define pr_fmt properly
x86/speculation/l1tf: Limit swap file size to MAX_PA/2
x86/speculation/l1tf: Disallow non privileged high MMIO PROT_NONE mappings
mm: fix cache mode tracking in vm_insert_mixed()
mm: Add vm_insert_pfn_prot()
x86/speculation/l1tf: Add sysfs reporting for l1tf
x86/speculation/l1tf: Make sure the first page is always reserved
x86/speculation/l1tf: Protect PROT_NONE PTEs against speculation
x86/speculation/l1tf: Protect swap entries against L1TF
x86/speculation/l1tf: Change order of offset/type in swap entry
mm: x86: move _PAGE_SWP_SOFT_DIRTY from bit 7 to bit 1
x86/mm: Fix swap entry comment and macro
x86/mm: Move swap offset/type up in PTE to work around erratum
x86/speculation/l1tf: Increase 32bit PAE __PHYSICAL_PAGE_SHIFT
x86/irqflags: Provide a declaration for native_save_fl
kprobes/x86: Fix %p uses in error messages
x86/speculation: Protect against userspace-userspace spectreRSB
x86/paravirt: Fix spectre-v2 mitigations for paravirt guests
ARM: dts: imx6sx: fix irq for pcie bridge
IB/ocrdma: fix out of bounds access to local buffer
IB/mlx4: Mark user MR as writable if actual virtual memory is writable
IB/core: Make testing MR flags for writability a static inline function
fix __legitimize_mnt()/mntput() race
fix mntput/mntput race
root dentries need RCU-delayed freeing
scsi: sr: Avoid that opening a CD-ROM hangs with runtime power management enabled
ACPI / LPSS: Add missing prv_offset setting for byt/cht PWM devices
xen/netfront: don't cache skb_shinfo()
parisc: Define mb() and add memory barriers to assembler unlock sequences
parisc: Enable CONFIG_MLONGCALLS by default
fork: unconditionally clear stack on fork
ipv4+ipv6: Make INET*_ESP select CRYPTO_ECHAINIV
tpm: fix race condition in tpm_common_write()
ext4: fix check to prevent initializing reserved inodes
Linux 4.4.147
jfs: Fix inconsistency between memory allocation and ea_buf->max_size
i2c: imx: Fix reinit_completion() use
ring_buffer: tracing: Inherit the tracing setting to next ring buffer
ACPI / PCI: Bail early in acpi_pci_add_bus() if there is no ACPI handle
ext4: fix false negatives *and* false positives in ext4_check_descriptors()
netlink: Don't shift on 64 for ngroups
netlink: Don't shift with UB on nlk->ngroups
netlink: Do not subscribe to non-existent groups
nohz: Fix local_timer_softirq_pending()
genirq: Make force irq threading setup more robust
scsi: qla2xxx: Return error when TMF returns
scsi: qla2xxx: Fix ISP recovery on unload
Conflicts:
include/linux/swapfile.h
Removed CONFIG_CRYPTO_ECHAINIV from defconfig files since this upmerge is
adding this config to Kconfig file.
Change-Id: Ide96c29f919d76590c2bdccf356d1d464a892fd7
Signed-off-by: Srinivasarao P <spathi@codeaurora.org>
Diffstat (limited to 'drivers/char/tpm/tpm-dev.c')
| -rw-r--r-- | drivers/char/tpm/tpm-dev.c | 43 |
1 files changed, 20 insertions, 23 deletions
diff --git a/drivers/char/tpm/tpm-dev.c b/drivers/char/tpm/tpm-dev.c index 912ad30be585..4719aa781bf2 100644 --- a/drivers/char/tpm/tpm-dev.c +++ b/drivers/char/tpm/tpm-dev.c @@ -25,7 +25,7 @@ struct file_priv { struct tpm_chip *chip; /* Data passed to and from the tpm via the read/write calls */ - atomic_t data_pending; + size_t data_pending; struct mutex buffer_mutex; struct timer_list user_read_timer; /* user needs to claim result */ @@ -46,7 +46,7 @@ static void timeout_work(struct work_struct *work) struct file_priv *priv = container_of(work, struct file_priv, work); mutex_lock(&priv->buffer_mutex); - atomic_set(&priv->data_pending, 0); + priv->data_pending = 0; memset(priv->data_buffer, 0, sizeof(priv->data_buffer)); mutex_unlock(&priv->buffer_mutex); } @@ -72,7 +72,6 @@ static int tpm_open(struct inode *inode, struct file *file) } priv->chip = chip; - atomic_set(&priv->data_pending, 0); mutex_init(&priv->buffer_mutex); setup_timer(&priv->user_read_timer, user_reader_timeout, (unsigned long)priv); @@ -86,28 +85,24 @@ static ssize_t tpm_read(struct file *file, char __user *buf, size_t size, loff_t *off) { struct file_priv *priv = file->private_data; - ssize_t ret_size; + ssize_t ret_size = 0; int rc; del_singleshot_timer_sync(&priv->user_read_timer); flush_work(&priv->work); - ret_size = atomic_read(&priv->data_pending); - if (ret_size > 0) { /* relay data */ - ssize_t orig_ret_size = ret_size; - if (size < ret_size) - ret_size = size; + mutex_lock(&priv->buffer_mutex); - mutex_lock(&priv->buffer_mutex); + if (priv->data_pending) { + ret_size = min_t(ssize_t, size, priv->data_pending); rc = copy_to_user(buf, priv->data_buffer, ret_size); - memset(priv->data_buffer, 0, orig_ret_size); + memset(priv->data_buffer, 0, priv->data_pending); if (rc) ret_size = -EFAULT; - mutex_unlock(&priv->buffer_mutex); + priv->data_pending = 0; } - atomic_set(&priv->data_pending, 0); - + mutex_unlock(&priv->buffer_mutex); return ret_size; } @@ -118,18 +113,20 @@ static ssize_t tpm_write(struct file *file, const char __user *buf, size_t in_size = size; ssize_t out_size; - /* cannot perform a write until the read has cleared - either via tpm_read or a user_read_timer timeout. - This also prevents splitted buffered writes from blocking here. - */ - if (atomic_read(&priv->data_pending) != 0) - return -EBUSY; - if (in_size > TPM_BUFSIZE) return -E2BIG; mutex_lock(&priv->buffer_mutex); + /* Cannot perform a write until the read has cleared either via + * tpm_read or a user_read_timer timeout. This also prevents split + * buffered writes from blocking here. + */ + if (priv->data_pending != 0) { + mutex_unlock(&priv->buffer_mutex); + return -EBUSY; + } + if (copy_from_user (priv->data_buffer, (void __user *) buf, in_size)) { mutex_unlock(&priv->buffer_mutex); @@ -153,7 +150,7 @@ static ssize_t tpm_write(struct file *file, const char __user *buf, return out_size; } - atomic_set(&priv->data_pending, out_size); + priv->data_pending = out_size; mutex_unlock(&priv->buffer_mutex); /* Set a timeout by which the reader must come claim the result */ @@ -172,7 +169,7 @@ static int tpm_release(struct inode *inode, struct file *file) del_singleshot_timer_sync(&priv->user_read_timer); flush_work(&priv->work); file->private_data = NULL; - atomic_set(&priv->data_pending, 0); + priv->data_pending = 0; clear_bit(0, &priv->chip->is_open); kfree(priv); return 0; |
