<commit_before>/*
 * sca3000_ring.c -- support VTI sca3000 series accelerometers via SPI
 *
 * This program is free software; you can redistribute it and/or modify it
 * under the terms of the GNU General Public License version 2 as published by
 * the Free Software Foundation.
 *
 * Copyright (c) 2009 <NAME> <<EMAIL>>
 *
 */

#include <linux/interrupt.h>
#include <linux/fs.h>
#include <linux/slab.h>
#include <linux/kernel.h>
#include <linux/spi/spi.h>
#include <linux/sysfs.h>
#include <linux/sched.h>
#include <linux/poll.h>

#include <linux/iio/iio.h>
#include <linux/iio/sysfs.h>
#include <linux/iio/buffer.h>
#include "../ring_hw.h"
#include "sca3000.h"

/* RFC / future work
 *
 * The internal ring buffer doesn't actually change what it holds depending
 * on which signals are enabled etc, merely whether you can read them.
 * As such the scan mode selection is somewhat different than for a software
 * ring buffer and changing it actually covers any data already in the buffer.
 * Currently scan elements aren't configured so it doesn't matter.
 */

static int sca3000_read_data(struct sca3000_state *st,
			    uint8_t reg_address_high,
			    u8 **rx_p,
			    int len)
{
	int ret;
	struct spi_transfer xfer[2] = {
		{
			.len = 1,
			.tx_buf = st->tx,
		}, {
			.len = len,
		}
	};
	*rx_p = kmalloc(len, GFP_KERNEL);
	if (*rx_p == NULL) {
		ret = -ENOMEM;
		goto error_ret;
	}
	xfer[1].rx_buf = *rx_p;
	st->tx[0] = SCA3000_READ_REG(reg_address_high);
	ret = spi_sync_transfer(st->us, xfer, ARRAY_SIZE(xfer));
	if (ret) {
		dev_err(get_device(&st->us->dev), "problem reading register");
		goto error_free_rx;
	}

	return 0;
error_free_rx:
	kfree(*rx_p);
error_ret:
	return ret;
}

/**
 * sca3000_read_first_n_hw_rb() - main ring access, pulls data from ring
 * @r:			the ring
 * @count:		number of samples to try and pull
 * @data:		output the actual samples pulled from the hw ring
 *
 * Currently does not provide timestamps.  As the hardware doesn't add them they
 * can only be inferred approximately from ring buffer events such as 50% full
 * and knowledge of when buffer was last emptied.  This is left to userspace.
 **/
static int sca3000_read_first_n_hw_rb(struct iio_buffer *r,
				      size_t count, char __user *buf)
{
	struct iio_hw_buffer *hw_ring = iio_to_hw_buf(r);
	struct iio_dev *indio_dev = hw_ring->private;
	struct sca3000_state *st = iio_priv(indio_dev);
	u8 *rx;
	int ret, i, num_available, num_read = 0;
	int bytes_per_sample = 1;

	if (st->bpse == 11)
		bytes_per_sample = 2;

	mutex_lock(&st->lock);
	if (count % bytes_per_sample) {
		ret = -EINVAL;
		goto error_ret;
	}

	ret = sca3000_read_data_short(st, SCA3000_REG_ADDR_BUF_COUNT, 1);
	if (ret)
		goto error_ret;
	else
		num_available = st->rx[0];
	/*
	 * num_available is the total number of samples available
	 * i.e. number of time points * number of channels.
	 */
	if (count > num_available * bytes_per_sample)
		num_read = num_available*bytes_per_sample;
	else
		num_read = count;

	ret = sca3000_read_data(st,
				SCA3000_REG_ADDR_RING_OUT,
				&rx, num_read);
	if (ret)
		goto error_ret;

	for (i = 0; i < num_read; i++)
		*(((u16 *)rx) + i) = be16_to_cpup((__be16 *)rx + i);

	if (copy_to_user(buf, rx, num_read))
		ret = -EFAULT;
	kfree(rx);
	r->stufftoread = 0;
error_ret:
	mutex_unlock(&st->lock);

	return ret ? ret : num_read;
}

static size_t sca3000_ring_buf_data_available(struct iio_buffer *r)
{
	return r->stufftoread ? r->watermark : 0;
}

/**
 * sca3000_query_ring_int() is the hardware ring status interrupt enabled
 **/
static ssize_t sca3000_query_ring_int(struct device *dev,<commit_msg>iio: accel: sca3000: memory corruption in sca3000_read_first_n_hw_rb()<commit_after>/*
 * sca3000_ring.c -- support VTI sca3000 series accelerometers via SPI
 *
 * This program is free software; you can redistribute it and/or modify it
 * under the terms of the GNU General Public License version 2 as published by
 * the Free Software Foundation.
 *
 * Copyright (c) 2009 <NAME> <<EMAIL>>
 *
 */

#include <linux/interrupt.h>
#include <linux/fs.h>
#include <linux/slab.h>
#include <linux/kernel.h>
#include <linux/spi/spi.h>
#include <linux/sysfs.h>
#include <linux/sched.h>
#include <linux/poll.h>

#include <linux/iio/iio.h>
#include <linux/iio/sysfs.h>
#include <linux/iio/buffer.h>
#include "../ring_hw.h"
#include "sca3000.h"

/* RFC / future work
 *
 * The internal ring buffer doesn't actually change what it holds depending
 * on which signals are enabled etc, merely whether you can read them.
 * As such the scan mode selection is somewhat different than for a software
 * ring buffer and changing it actually covers any data already in the buffer.
 * Currently scan elements aren't configured so it doesn't matter.
 */

static int sca3000_read_data(struct sca3000_state *st,
			    uint8_t reg_address_high,
			    u8 **rx_p,
			    int len)
{
	int ret;
	struct spi_transfer xfer[2] = {
		{
			.len = 1,
			.tx_buf = st->tx,
		}, {
			.len = len,
		}
	};
	*rx_p = kmalloc(len, GFP_KERNEL);
	if (*rx_p == NULL) {
		ret = -ENOMEM;
		goto error_ret;
	}
	xfer[1].rx_buf = *rx_p;
	st->tx[0] = SCA3000_READ_REG(reg_address_high);
	ret = spi_sync_transfer(st->us, xfer, ARRAY_SIZE(xfer));
	if (ret) {
		dev_err(get_device(&st->us->dev), "problem reading register");
		goto error_free_rx;
	}

	return 0;
error_free_rx:
	kfree(*rx_p);
error_ret:
	return ret;
}

/**
 * sca3000_read_first_n_hw_rb() - main ring access, pulls data from ring
 * @r:			the ring
 * @count:		number of samples to try and pull
 * @data:		output the actual samples pulled from the hw ring
 *
 * Currently does not provide timestamps.  As the hardware doesn't add them they
 * can only be inferred approximately from ring buffer events such as 50% full
 * and knowledge of when buffer was last emptied.  This is left to userspace.
 **/
static int sca3000_read_first_n_hw_rb(struct iio_buffer *r,
				      size_t count, char __user *buf)
{
	struct iio_hw_buffer *hw_ring = iio_to_hw_buf(r);
	struct iio_dev *indio_dev = hw_ring->private;
	struct sca3000_state *st = iio_priv(indio_dev);
	u8 *rx;
	int ret, i, num_available, num_read = 0;
	int bytes_per_sample = 1;

	if (st->bpse == 11)
		bytes_per_sample = 2;

	mutex_lock(&st->lock);
	if (count % bytes_per_sample) {
		ret = -EINVAL;
		goto error_ret;
	}

	ret = sca3000_read_data_short(st, SCA3000_REG_ADDR_BUF_COUNT, 1);
	if (ret)
		goto error_ret;
	else
		num_available = st->rx[0];
	/*
	 * num_available is the total number of samples available
	 * i.e. number of time points * number of channels.
	 */
	if (count > num_available * bytes_per_sample)
		num_read = num_available*bytes_per_sample;
	else
		num_read = count;

	ret = sca3000_read_data(st,
				SCA3000_REG_ADDR_RING_OUT,
				&rx, num_read);
	if (ret)
		goto error_ret;

	for (i = 0; i < num_read / sizeof(u16); i++)
		*(((u16 *)rx) + i) = be16_to_cpup((__be16 *)rx + i);

	if (copy_to_user(buf, rx, num_read))
		ret = -EFAULT;
	kfree(rx);
	r->stufftoread = 0;
error_ret:
	mutex_unlock(&st->lock);

	return ret ? ret : num_read;
}

static size_t sca3000_ring_buf_data_available(struct iio_buffer *r)
{
	return r->stufftoread ? r->watermark : 0;
}

/**
 * sca3000_query_ring_int() is the hardware ring status interrupt enabled
 **/
static ssize_t sca3000_query_ring_int(struct device *dev,
{'fraction_non_alphanumeric': 0.11658208750514333, 'fraction_numerical': 0.0274310794129749, 'mean_word_length': 3.9137466307277626, 'pattern_counts': {'":': 0, '<': 33, '<?xml version=': 0, '>': 59, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '4925781', 'n_tokens_mistral': 2971, 'n_tokens_neox': 2704, 'n_words': 792}