Merge "kernel: enable internaldb on perf build"
diff --git a/arch/arm/configs/msm8610-perf_defconfig b/arch/arm/configs/msm8610-perf_defconfig
index 462b5c3..bd135b3 100644
--- a/arch/arm/configs/msm8610-perf_defconfig
+++ b/arch/arm/configs/msm8610-perf_defconfig
@@ -78,7 +78,6 @@
CONFIG_KSM=y
CONFIG_CC_STACKPROTECTOR=y
CONFIG_KSM=y
-CONFIG_ENABLE_VMALLOC_SAVING=y
CONFIG_CP_ACCESS=y
CONFIG_USE_OF=y
CONFIG_CPU_FREQ_GOV_POWERSAVE=y
diff --git a/arch/arm/configs/msm8610_defconfig b/arch/arm/configs/msm8610_defconfig
index 899ed30..f6ef804 100644
--- a/arch/arm/configs/msm8610_defconfig
+++ b/arch/arm/configs/msm8610_defconfig
@@ -79,7 +79,6 @@
CONFIG_KSM=y
CONFIG_CC_STACKPROTECTOR=y
CONFIG_KSM=y
-CONFIG_ENABLE_VMALLOC_SAVING=y
CONFIG_CP_ACCESS=y
CONFIG_USE_OF=y
CONFIG_CPU_FREQ_GOV_POWERSAVE=y
diff --git a/arch/arm/mach-msm/Kconfig b/arch/arm/mach-msm/Kconfig
index 4b8d443..f84ea26 100644
--- a/arch/arm/mach-msm/Kconfig
+++ b/arch/arm/mach-msm/Kconfig
@@ -475,7 +475,6 @@
select MSM_RPM_LOG
select MSM_IOMMU_SYNC
select MSM_RPM_STATS_LOG
- select ENABLE_VMALLOC_SAVINGS
config ARCH_MSM8226
bool "MSM8226"
diff --git a/arch/arm/mm/mmu.c b/arch/arm/mm/mmu.c
index a1a2e51..669b10e 100644
--- a/arch/arm/mm/mmu.c
+++ b/arch/arm/mm/mmu.c
@@ -1500,7 +1500,9 @@
vm->flags = VM_LOWMEM | VM_ARM_STATIC_MAPPING;
vm->flags |= VM_ARM_MTYPE(type);
vm->caller = map_lowmem;
- vm_area_add_early(vm++);
+ vm_area_add_early(vm);
+ mark_vmalloc_reserved_area(vm->addr, vm->size);
+ vm++;
}
}
diff --git a/drivers/gpu/msm/adreno_dispatch.c b/drivers/gpu/msm/adreno_dispatch.c
index 2da36b6..ec5e57c 100644
--- a/drivers/gpu/msm/adreno_dispatch.c
+++ b/drivers/gpu/msm/adreno_dispatch.c
@@ -1515,8 +1515,14 @@
*/
void adreno_dispatcher_start(struct kgsl_device *device)
{
+ struct adreno_device *adreno_dev = ADRENO_DEVICE(device);
+
complete_all(&device->cmdbatch_gate);
+ /* a305c GPU is slower than a330 and needs a larger timer */
+ if (adreno_is_a305c(adreno_dev))
+ _fault_timer_interval = 200;
+
/* Schedule the work loop to get things going */
adreno_dispatcher_schedule(device);
}
diff --git a/drivers/hwmon/epm_adc.c b/drivers/hwmon/epm_adc.c
index f7cf2df..2f5ed9d 100644
--- a/drivers/hwmon/epm_adc.c
+++ b/drivers/hwmon/epm_adc.c
@@ -888,6 +888,12 @@
init_resp->num_dev = rx_buf[6];
init_resp->num_channel = rx_buf[7];
+ pr_debug("EPM PSOC response for hello command: resp_cmd:0x%x\n",
+ rx_buf[0]);
+ pr_debug("EPM PSOC version:0x%x\n", rx_buf[1]);
+ pr_debug("EPM PSOC firmware version:0x%x\n",
+ rx_buf[6] | rx_buf[5] | rx_buf[4] | rx_buf[3]);
+
return rc;
}
diff --git a/drivers/input/misc/bmp18x-core.c b/drivers/input/misc/bmp18x-core.c
index 001a804..3949f6e 100644
--- a/drivers/input/misc/bmp18x-core.c
+++ b/drivers/input/misc/bmp18x-core.c
@@ -88,6 +88,7 @@
struct device *dev;
struct mutex lock;
struct bmp18x_calibration_data calibration;
+ struct sensors_classdev cdev;
u8 oversampling_setting;
u8 sw_oversampling_setting;
u32 raw_temperature;
@@ -113,9 +114,13 @@
.max_range = "1100.0",
.resolution = "0.01",
.sensor_power = "0.67",
- .min_delay = 20000,
+ .min_delay = 20000, /* microsecond */
.fifo_reserved_event_count = 0,
.fifo_max_event_count = 0,
+ .enabled = 0,
+ .delay_msec = 200, /* millisecond */
+ .sensors_enable = NULL,
+ .sensors_poll_delay = NULL,
};
#ifdef CONFIG_HAS_EARLYSUSPEND
@@ -403,6 +408,19 @@
static DEVICE_ATTR(sw_oversampling, S_IWUSR | S_IRUGO,
show_sw_oversampling, set_sw_oversampling);
+static ssize_t bmp18x_poll_delay_set(struct sensors_classdev *sensors_cdev,
+ unsigned int delay_msec)
+{
+ struct bmp18x_data *data = container_of(sensors_cdev,
+ struct bmp18x_data, cdev);
+ mutex_lock(&data->lock);
+ data->delay = delay_msec;
+ mutex_unlock(&data->lock);
+
+ return 0;
+}
+
+
static ssize_t show_delay(struct device *dev,
struct device_attribute *attr, char *buf)
{
@@ -416,17 +434,43 @@
{
struct bmp18x_data *data = dev_get_drvdata(dev);
unsigned long delay;
- int success = kstrtoul(buf, 10, &delay);
- if (success == 0) {
- mutex_lock(&data->lock);
- data->delay = delay;
- mutex_unlock(&data->lock);
- }
- return success;
+ int err = kstrtoul(buf, 10, &delay);
+ if (err < 0)
+ return err;
+
+ err = bmp18x_poll_delay_set(&data->cdev, delay);
+ if (err < 0)
+ return err;
+
+ return count;
}
+
static DEVICE_ATTR(delay, S_IWUSR | S_IRUGO,
show_delay, set_delay);
+static ssize_t bmp18x_enable_set(struct sensors_classdev *sensors_cdev,
+ unsigned int enabled)
+{
+ struct bmp18x_data *data = container_of(sensors_cdev,
+ struct bmp18x_data, cdev);
+ struct device *dev = data->dev;
+
+ mutex_lock(&data->lock);
+ data->enable = enabled ? 1 : 0;
+
+ if (data->enable) {
+ bmp18x_enable(dev);
+ schedule_delayed_work(&data->work,
+ msecs_to_jiffies(data->delay));
+ } else {
+ cancel_delayed_work_sync(&data->work);
+ bmp18x_disable(dev);
+ }
+ mutex_unlock(&data->lock);
+
+ return 0;
+}
+
static ssize_t show_enable(struct device *dev,
struct device_attribute *attr, char *buf)
{
@@ -440,24 +484,17 @@
{
struct bmp18x_data *data = dev_get_drvdata(dev);
unsigned long enable;
- int success = kstrtoul(buf, 10, &enable);
- if (success == 0) {
- mutex_lock(&data->lock);
- data->enable = enable ? 1 : 0;
+ int err = kstrtoul(buf, 10, &enable);
+ if (err < 0)
+ return err;
- if (data->enable) {
- bmp18x_enable(dev);
- schedule_delayed_work(&data->work,
- msecs_to_jiffies(data->delay));
- } else {
- cancel_delayed_work_sync(&data->work);
- bmp18x_disable(dev);
- }
- mutex_unlock(&data->lock);
+ err = bmp18x_enable_set(&data->cdev, enable);
+ if (err < 0)
+ return err;
- }
return count;
}
+
static DEVICE_ATTR(enable, S_IWUSR | S_IRUGO,
show_enable, set_enable);
@@ -628,7 +665,10 @@
if (err)
goto error_sysfs;
- err = sensors_classdev_register(&data->input->dev, &sensors_cdev);
+ data->cdev = sensors_cdev;
+ data->cdev.sensors_enable = bmp18x_enable_set;
+ data->cdev.sensors_poll_delay = bmp18x_poll_delay_set;
+ err = sensors_classdev_register(&data->input->dev, &data->cdev);
if (err) {
pr_err("class device create failed: %d\n", err);
goto error_class_sysfs;
diff --git a/drivers/input/misc/cm36283.c b/drivers/input/misc/cm36283.c
index 5c89c0c..5f08da4 100644
--- a/drivers/input/misc/cm36283.c
+++ b/drivers/input/misc/cm36283.c
@@ -640,12 +640,6 @@
.unlocked_ioctl = psensor_ioctl
};
-struct miscdevice psensor_misc = {
- .minor = MISC_DYNAMIC_MINOR,
- .name = "proximity",
- .fops = &psensor_fops
-};
-
void lightsensor_set_kvalue(struct cm36283_info *lpi)
{
if (!lpi) {
@@ -793,13 +787,6 @@
.unlocked_ioctl = lightsensor_ioctl
};
-static struct miscdevice lightsensor_misc = {
- .minor = MISC_DYNAMIC_MINOR,
- .name = "lightsensor",
- .fops = &lightsensor_fops
-};
-
-
static ssize_t ps_adc_show(struct device *dev,
struct device_attribute *attr, char *buf)
{
@@ -844,7 +831,6 @@
return count;
}
-static DEVICE_ATTR(ps_adc, 0664, ps_adc_show, ps_enable_store);
static ssize_t ps_parameters_show(struct device *dev,
struct device_attribute *attr, char *buf)
@@ -888,10 +874,6 @@
return count;
}
-static DEVICE_ATTR(ps_parameters, 0664,
- ps_parameters_show, ps_parameters_store);
-
-
static ssize_t ps_conf_show(struct device *dev,
struct device_attribute *attr, char *buf)
{
@@ -917,7 +899,6 @@
return count;
}
-static DEVICE_ATTR(ps_conf, 0664, ps_conf_show, ps_conf_store);
static ssize_t ps_thd_show(struct device *dev,
struct device_attribute *attr, char *buf)
@@ -946,7 +927,6 @@
return count;
}
-static DEVICE_ATTR(ps_thd, 0664, ps_thd_show, ps_thd_store);
static ssize_t ps_hw_show(struct device *dev,
struct device_attribute *attr, char *buf)
@@ -969,7 +949,6 @@
return count;
}
-static DEVICE_ATTR(ps_hw, 0664, ps_hw_show, ps_hw_store);
static ssize_t ls_adc_show(struct device *dev,
struct device_attribute *attr, char *buf)
@@ -983,8 +962,6 @@
return ret;
}
-static DEVICE_ATTR(ls_adc, 0664, ls_adc_show, NULL);
-
static ssize_t ls_enable_show(struct device *dev,
struct device_attribute *attr, char *buf)
{
@@ -1033,8 +1010,6 @@
return count;
}
-static DEVICE_ATTR(ls_auto, 0664,
- ls_enable_show, ls_enable_store);
static ssize_t ls_kadc_show(struct device *dev,
struct device_attribute *attr, char *buf)
@@ -1077,7 +1052,6 @@
return count;
}
-static DEVICE_ATTR(ls_kadc, 0664, ls_kadc_show, ls_kadc_store);
static ssize_t ls_gadc_show(struct device *dev,
struct device_attribute *attr, char *buf)
@@ -1117,7 +1091,6 @@
return count;
}
-static DEVICE_ATTR(ls_gadc, 0664, ls_gadc_show, ls_gadc_store);
static ssize_t ls_adc_table_show(struct device *dev,
struct device_attribute *attr, char *buf)
@@ -1168,9 +1141,6 @@
return count;
}
-static DEVICE_ATTR(ls_adc_table, 0664,
- ls_adc_table_show, ls_adc_table_store);
-
static ssize_t ls_conf_show(struct device *dev,
struct device_attribute *attr, char *buf)
{
@@ -1192,7 +1162,6 @@
_cm36283_I2C_Write_Word(lpi->slave_addr, ALS_CONF, lpi->ls_cmd);
return count;
}
-static DEVICE_ATTR(ls_conf, 0664, ls_conf_show, ls_conf_store);
static ssize_t ls_poll_delay_show(struct device *dev,
struct device_attribute *attr, char *buf)
@@ -1219,9 +1188,6 @@
return count;
}
-static DEVICE_ATTR(ls_poll_delay, 0664, ls_poll_delay_show,
- ls_poll_delay_store);
-
static ssize_t ps_poll_delay_show(struct device *dev,
struct device_attribute *attr, char *buf)
{
@@ -1247,9 +1213,6 @@
return count;
}
-static DEVICE_ATTR(ps_poll_delay, 0664, ps_poll_delay_show,
- ps_poll_delay_store);
-
static ssize_t ls_fLevel_show(struct device *dev,
struct device_attribute *attr, char *buf)
{
@@ -1271,7 +1234,6 @@
fLevel=-1;
return count;
}
-static DEVICE_ATTR(ls_flevel, 0664, ls_fLevel_show, ls_fLevel_store);
static int lightsensor_setup(struct cm36283_info *lpi)
{
@@ -1286,6 +1248,7 @@
return -ENOMEM;
}
lpi->ls_input_dev->name = "cm36283-ls";
+ lpi->ls_input_dev->id.bustype = BUS_I2C;
set_bit(EV_ABS, lpi->ls_input_dev->evbit);
range = get_als_range();
@@ -1298,17 +1261,8 @@
goto err_free_ls_input_device;
}
- ret = misc_register(&lightsensor_misc);
- if (ret < 0) {
- pr_err("[LS][CM36283 error]%s: can not register ls misc device\n",
- __func__);
- goto err_unregister_ls_input_device;
- }
-
return ret;
-err_unregister_ls_input_device:
- input_unregister_device(lpi->ls_input_dev);
err_free_ls_input_device:
input_free_device(lpi->ls_input_dev);
return ret;
@@ -1326,6 +1280,7 @@
return -ENOMEM;
}
lpi->ps_input_dev->name = "cm36283-ps";
+ lpi->ps_input_dev->id.bustype = BUS_I2C;
set_bit(EV_ABS, lpi->ps_input_dev->evbit);
input_set_abs_params(lpi->ps_input_dev, ABS_DISTANCE, 0, 1, 0, 0);
@@ -1337,18 +1292,8 @@
goto err_free_ps_input_device;
}
- ret = misc_register(&psensor_misc);
- if (ret < 0) {
- pr_err(
- "[PS][CM36283 error]%s: could not register ps misc device\n",
- __func__);
- goto err_unregister_ps_input_device;
- }
-
return ret;
-err_unregister_ps_input_device:
- input_unregister_device(lpi->ps_input_dev);
err_free_ps_input_device:
input_free_device(lpi->ps_input_dev);
return ret;
@@ -1496,6 +1441,59 @@
return 0;
}
+static int create_sysfs_interfaces(struct device *dev,
+ struct device_attribute *attributes, int len)
+{
+ int i;
+ int err;
+ for (i = 0; i < len; i++) {
+ err = device_create_file(dev, attributes + i);
+ if (err)
+ goto error;
+ }
+ return 0;
+
+error:
+ for (; i >= 0; i--)
+ device_remove_file(dev, attributes + i);
+ dev_err(dev, "%s:Unable to create interface\n", __func__);
+ return err;
+}
+
+static int remove_sysfs_interfaces(struct device *dev,
+ struct device_attribute *attributes, int len)
+{
+ int i;
+ for (i = 0; i < len; i++)
+ device_remove_file(dev, attributes + i);
+ return 0;
+}
+
+static struct device_attribute light_attr[] = {
+ __ATTR(ls_adc, 0664, ls_adc_show, NULL),
+ __ATTR(ls_kadc, 0664, ls_kadc_show, ls_kadc_store),
+ __ATTR(ls_gadc, 0664, ls_gadc_show, ls_gadc_store),
+ __ATTR(ls_conf, 0664, ls_conf_show, ls_conf_store),
+ __ATTR(ls_adc_table, 0664,
+ ls_adc_table_show, ls_adc_table_store),
+ __ATTR(poll_delay, 0664, ls_poll_delay_show,
+ ls_poll_delay_store),
+ __ATTR(enable, 0664,
+ ls_enable_show, ls_enable_store),
+};
+
+static struct device_attribute proximity_attr[] = {
+ __ATTR(enable, 0664, ps_adc_show, ps_enable_store),
+ __ATTR(ps_parameters, 0664,
+ ps_parameters_show, ps_parameters_store),
+ __ATTR(ps_conf, 0664, ps_conf_show, ps_conf_store),
+ __ATTR(ps_hw, 0664, ps_hw_show, ps_hw_store),
+ __ATTR(ps_thd, 0664, ps_thd_show, ps_thd_store),
+ __ATTR(poll_delay, 0664, ps_poll_delay_show,
+ ps_poll_delay_store),
+ __ATTR(ls_flevel, 0664, ls_fLevel_show, ls_fLevel_store),
+};
+
static int cm36283_probe(struct i2c_client *client,
const struct i2c_device_id *id)
{
@@ -1633,95 +1631,24 @@
goto err_psensor_setup;
}
- lpi->cm36283_class = class_create(THIS_MODULE, "optical_sensors");
- if (IS_ERR(lpi->cm36283_class)) {
- ret = PTR_ERR(lpi->cm36283_class);
- lpi->cm36283_class = NULL;
- goto err_create_class;
+ ret = create_sysfs_interfaces(&lpi->ls_input_dev->dev, light_attr,
+ ARRAY_SIZE(light_attr));
+ if (ret < 0) {
+ dev_err(&client->dev, "failed to create sysfs\n");
+ goto err_input_cleanup;
}
- lpi->ls_dev = device_create(lpi->cm36283_class,
- NULL, 0, "%s", "lightsensor");
- if (unlikely(IS_ERR(lpi->ls_dev))) {
- ret = PTR_ERR(lpi->ls_dev);
- lpi->ls_dev = NULL;
- goto err_create_ls_device;
+ ret = create_sysfs_interfaces(&lpi->ps_input_dev->dev, proximity_attr,
+ ARRAY_SIZE(proximity_attr));
+ if (ret < 0) {
+ dev_err(&client->dev, "failed to create sysfs\n");
+ goto err_light_sysfs_cleanup;
}
- /* register the attributes */
- ret = device_create_file(lpi->ls_dev, &dev_attr_ls_adc);
- if (ret)
- goto err_create_ls_device_file;
-
- /* register the attributes */
- ret = device_create_file(lpi->ls_dev, &dev_attr_ls_auto);
- if (ret)
- goto err_create_ls_device_file;
-
- /* register the attributes */
- ret = device_create_file(lpi->ls_dev, &dev_attr_ls_kadc);
- if (ret)
- goto err_create_ls_device_file;
-
- ret = device_create_file(lpi->ls_dev, &dev_attr_ls_gadc);
- if (ret)
- goto err_create_ls_device_file;
-
- ret = device_create_file(lpi->ls_dev, &dev_attr_ls_adc_table);
- if (ret)
- goto err_create_ls_device_file;
-
- ret = device_create_file(lpi->ls_dev, &dev_attr_ls_conf);
- if (ret)
- goto err_create_ls_device_file;
-
- ret = device_create_file(lpi->ls_dev, &dev_attr_ls_flevel);
- if (ret)
- goto err_create_ls_device_file;
-
- ret = device_create_file(lpi->ls_dev, &dev_attr_ls_poll_delay);
- if (ret)
- goto err_create_ls_device_file;
-
- lpi->ps_dev = device_create(lpi->cm36283_class,
- NULL, 0, "%s", "proximity");
- if (unlikely(IS_ERR(lpi->ps_dev))) {
- ret = PTR_ERR(lpi->ps_dev);
- lpi->ps_dev = NULL;
- goto err_create_ps_device;
- }
-
- /* register the attributes */
- ret = device_create_file(lpi->ps_dev, &dev_attr_ps_adc);
- if (ret)
- goto err_create_ps_device_file;
-
- ret = device_create_file(lpi->ps_dev,
- &dev_attr_ps_parameters);
- if (ret)
- goto err_create_ps_device_file;
-
- /* register the attributes */
- ret = device_create_file(lpi->ps_dev, &dev_attr_ps_conf);
- if (ret)
- goto err_create_ps_device_file;
-
- /* register the attributes */
- ret = device_create_file(lpi->ps_dev, &dev_attr_ps_thd);
- if (ret)
- goto err_create_ps_device_file;
-
- ret = device_create_file(lpi->ps_dev, &dev_attr_ps_hw);
- if (ret)
- goto err_create_ps_device_file;
-
- ret = device_create_file(lpi->ps_dev, &dev_attr_ps_poll_delay);
- if (ret)
- goto err_create_ps_device_file;
ret = sensors_classdev_register(&client->dev, &sensors_light_cdev);
if (ret)
- goto err_create_ps_device_file;
+ goto err_proximity_sysfs_cleanup;
ret = sensors_classdev_register(&client->dev, &sensors_proximity_cdev);
if (ret)
@@ -1735,19 +1662,16 @@
return ret;
err_create_class_sysfs:
sensors_classdev_unregister(&sensors_light_cdev);
-err_create_ps_device_file:
- device_unregister(lpi->ps_dev);
-err_create_ps_device:
-err_create_ls_device_file:
- device_unregister(lpi->ls_dev);
-err_create_ls_device:
- class_destroy(lpi->cm36283_class);
-err_create_class:
- misc_deregister(&psensor_misc);
+err_proximity_sysfs_cleanup:
+ remove_sysfs_interfaces(&lpi->ps_input_dev->dev, proximity_attr,
+ ARRAY_SIZE(proximity_attr));
+err_light_sysfs_cleanup:
+ remove_sysfs_interfaces(&lpi->ls_input_dev->dev, light_attr,
+ ARRAY_SIZE(light_attr));
+err_input_cleanup:
input_unregister_device(lpi->ps_input_dev);
input_free_device(lpi->ps_input_dev);
err_psensor_setup:
- misc_deregister(&lightsensor_misc);
input_unregister_device(lpi->ls_input_dev);
input_free_device(lpi->ls_input_dev);
err_lightsensor_setup:
diff --git a/drivers/input/touchscreen/gt9xx/gt9xx.c b/drivers/input/touchscreen/gt9xx/gt9xx.c
index b39cb0d..7fa6c39 100644
--- a/drivers/input/touchscreen/gt9xx/gt9xx.c
+++ b/drivers/input/touchscreen/gt9xx/gt9xx.c
@@ -753,16 +753,13 @@
return ret;
}
#else
-/*******************************************************
-Function:
- Enter sleep mode.
-Input:
- ts: private data.
-Output:
- Executive outcomes.
- >0: succeed, otherwise failed.
-*******************************************************/
-static s8 gtp_enter_sleep(struct goodix_ts_data *ts)
+/**
+ * gtp_enter_sleep - Enter sleep mode
+ * @ts: driver private data
+ *
+ * Returns zero on success, else an error.
+ */
+static u8 gtp_enter_sleep(struct goodix_ts_data *ts)
{
int ret = -1;
s8 retry = 0;
@@ -784,16 +781,16 @@
ret = goodix_power_off(ts);
if (ret) {
dev_err(&ts->client->dev, "GTP power off failed.\n");
- return 0;
+ return ret;
}
- return 1;
+ return 0;
} else {
usleep(5000);
while (retry++ < 5) {
ret = gtp_i2c_write(ts->client, i2c_control_buf, 3);
if (ret == 1) {
dev_dbg(&ts->client->dev, "GTP enter sleep!");
- return ret;
+ return 0;
}
msleep(20);
}
@@ -2031,7 +2028,7 @@
ret = gtp_enter_sleep(ts);
#endif
- if (ret <= 0)
+ if (ret < 0)
dev_err(&ts->client->dev, "GTP early suspend failed.\n");
/* to avoid waking up while not sleeping,
* delay 48 + 10ms to ensure reliability
@@ -2268,8 +2265,15 @@
}
#endif
-static SIMPLE_DEV_PM_OPS(goodix_ts_dev_pm_ops, goodix_ts_suspend,
- goodix_ts_resume);
+#if (!defined(CONFIG_FB) && !defined(CONFIG_HAS_EARLYSUSPEND))
+static const struct dev_pm_ops goodix_ts_dev_pm_ops = {
+ .suspend = goodix_ts_suspend,
+ .resume = goodix_ts_resume,
+};
+#else
+static const struct dev_pm_ops goodix_ts_dev_pm_ops = {
+};
+#endif
static const struct i2c_device_id goodix_ts_id[] = {
{ GTP_I2C_NAME, 0 },
diff --git a/drivers/media/platform/msm/camera_v2/ispif/msm_ispif.c b/drivers/media/platform/msm/camera_v2/ispif/msm_ispif.c
index de098c9..c4a23ca 100755
--- a/drivers/media/platform/msm/camera_v2/ispif/msm_ispif.c
+++ b/drivers/media/platform/msm/camera_v2/ispif/msm_ispif.c
@@ -200,7 +200,7 @@
ispif->base + ISPIF_VFE_m_INTF_CMD_0(i));
msm_camera_io_w(ISPIF_STOP_INTF_IMMEDIATELY,
ispif->base + ISPIF_VFE_m_INTF_CMD_1(i));
- pr_debug("%s: base %x", __func__, (unsigned int)ispif->base);
+ pr_debug("%s: base %lx", __func__, (unsigned long)ispif->base);
msm_camera_io_w(0, ispif->base +
ISPIF_VFE_m_PIX_INTF_n_CID_MASK(i, 0));
msm_camera_io_w(0, ispif->base +
diff --git a/drivers/media/platform/msm/vidc/hfi_response_handler.c b/drivers/media/platform/msm/vidc/hfi_response_handler.c
index 3fd5d3a..189fca0 100644
--- a/drivers/media/platform/msm/vidc/hfi_response_handler.c
+++ b/drivers/media/platform/msm/vidc/hfi_response_handler.c
@@ -263,7 +263,9 @@
break;
case HFI_EVENT_RELEASE_BUFFER_REFERENCE:
dprintk(VIDC_INFO, "HFI_EVENT_RELEASE_BUFFER_REFERENCE\n");
- hfi_process_evt_release_buffer_ref(callback, device_id, pkt);
+ if (!validate_session_pkt(sessions, sess, session_lock))
+ hfi_process_evt_release_buffer_ref(callback,
+ device_id, pkt);
break;
default:
dprintk(VIDC_WARN, "hal_process_event_notify:unkown_event_id");
diff --git a/drivers/media/platform/msm/vidc/msm_vidc.c b/drivers/media/platform/msm/vidc/msm_vidc.c
index 9da1220..42ef64c 100644
--- a/drivers/media/platform/msm/vidc/msm_vidc.c
+++ b/drivers/media/platform/msm/vidc/msm_vidc.c
@@ -717,6 +717,8 @@
return -EINVAL;
list_for_each_safe(ptr, next, &inst->registered_bufs) {
+ bool release_buf = false;
+ mutex_lock(&inst->lock);
bi = list_entry(ptr, struct buffer_info, list);
if (bi->type == buffer_type) {
buffer_info.type = bi->type;
@@ -734,19 +736,28 @@
buffer_info.m.planes[i].length);
}
buffer_info.length = bi->num_planes;
- if (inst->session_type == MSM_VIDC_DECODER)
- rc = msm_vdec_release_buf(instance,
- &buffer_info);
- if (inst->session_type == MSM_VIDC_ENCODER)
- rc = msm_venc_release_buf(instance,
- &buffer_info);
- if (rc)
- dprintk(VIDC_ERR,
- "Failed Release buffer: %d, %d, %d\n",
- buffer_info.m.planes[0].reserved[0],
- buffer_info.m.planes[0].reserved[1],
- buffer_info.m.planes[0].length);
-
+ release_buf = true;
+ }
+ mutex_unlock(&inst->lock);
+ if (!release_buf)
+ continue;
+ if (inst->session_type == MSM_VIDC_DECODER)
+ rc = msm_vdec_release_buf(instance,
+ &buffer_info);
+ if (inst->session_type == MSM_VIDC_ENCODER)
+ rc = msm_venc_release_buf(instance,
+ &buffer_info);
+ if (rc)
+ dprintk(VIDC_ERR,
+ "Failed Release buffer: %d, %d, %d\n",
+ buffer_info.m.planes[0].reserved[0],
+ buffer_info.m.planes[0].reserved[1],
+ buffer_info.m.planes[0].length);
+ }
+ mutex_lock(&inst->lock);
+ list_for_each_safe(ptr, next, &inst->registered_bufs) {
+ bi = list_entry(ptr, struct buffer_info, list);
+ if (bi->type == buffer_type) {
list_del(&bi->list);
for (i = 0; i < bi->num_planes; i++) {
if (bi->handle[i] && bi->mapped[i]) {
@@ -762,6 +773,7 @@
kfree(bi);
}
}
+ mutex_unlock(&inst->lock);
return rc;
}
diff --git a/drivers/media/platform/msm/vidc/msm_vidc_common.c b/drivers/media/platform/msm/vidc/msm_vidc_common.c
index 7588994..8921b13 100644
--- a/drivers/media/platform/msm/vidc/msm_vidc_common.c
+++ b/drivers/media/platform/msm/vidc/msm_vidc_common.c
@@ -519,6 +519,14 @@
event_notify->packet_buffer,
event_notify->exra_data_buffer);
+ if (inst->state == MSM_VIDC_CORE_INVALID ||
+ inst->core->state ==
+ VIDC_CORE_INVALID) {
+ dprintk(VIDC_DBG,
+ "Event release buf ref received in invalid state - discard\n");
+ return;
+ }
+
/*
* Get the buffer_info entry for the
* device address.
@@ -2999,6 +3007,9 @@
dprintk(VIDC_INFO, "Input only flush not supported\n");
return 0;
}
+ mutex_lock(&inst->sync_lock);
+ msm_comm_flush_dynamic_buffers(inst);
+ mutex_unlock(&inst->sync_lock);
if (inst->state == MSM_VIDC_CORE_INVALID ||
core->state == VIDC_CORE_INVALID) {
dprintk(VIDC_ERR,
@@ -3009,7 +3020,6 @@
}
mutex_lock(&inst->sync_lock);
- msm_comm_flush_dynamic_buffers(inst);
if (inst->in_reconfig && !ip_flush && op_flush) {
if (!list_empty(&inst->pendingq)) {
/*Execution can never reach here since port reconfig
diff --git a/drivers/media/radio/radio-iris.c b/drivers/media/radio/radio-iris.c
index 5dde469..d4ce343 100644
--- a/drivers/media/radio/radio-iris.c
+++ b/drivers/media/radio/radio-iris.c
@@ -3625,13 +3625,21 @@
break;
case V4L2_CID_PRIVATE_IRIS_RIVA_POKE:
if (radio->riva_data_req.cmd_params.length <= MAX_RIVA_PEEK_RSP_SIZE) {
- memcpy(radio->riva_data_req.data, (void *)ctrl->value,
+ retval = copy_from_user(radio->riva_data_req.data,
+ (void *)ctrl->value,
radio->riva_data_req.cmd_params.length);
- radio->riva_data_req.cmd_params.subopcode = RIVA_POKE_OPCODE;
- retval = hci_poke_data(&radio->riva_data_req , radio->fm_hdev);
+ if (retval == 0) {
+ radio->riva_data_req.cmd_params.subopcode =
+ RIVA_POKE_OPCODE;
+ retval = hci_poke_data(&radio->riva_data_req,
+ radio->fm_hdev);
+ } else {
+ retval = -EINVAL;
+ }
} else {
FMDERR("Can not copy into driver's buffer. Length %d is more than"
- "the buffer size %d\n", ctrl->value, MAX_RIVA_PEEK_RSP_SIZE);
+ "the buffer size %d\n", radio->riva_data_req.cmd_params.length,
+ MAX_RIVA_PEEK_RSP_SIZE);
retval = -EINVAL;
}
break;
diff --git a/drivers/net/wireless/wcnss/wcnss_wlan.c b/drivers/net/wireless/wcnss/wcnss_wlan.c
index 12c5704..8e695c3 100644
--- a/drivers/net/wireless/wcnss/wcnss_wlan.c
+++ b/drivers/net/wireless/wcnss/wcnss_wlan.c
@@ -45,6 +45,7 @@
#endif
#define DEVICE "wcnss_wlan"
+#define CTRL_DEVICE "wcnss_ctrl"
#define VERSION "1.01"
#define WCNSS_PIL_DEVICE "wcnss"
@@ -157,6 +158,14 @@
#define WCNSS_MAX_FRAME_SIZE (4*1024)
#define WCNSS_VERSION_LEN 30
#define WCNSS_MAX_BUILD_VER_LEN 256
+#define WCNSS_MAX_CMD_LEN (128)
+#define WCNSS_MIN_CMD_LEN (3)
+#define WCNSS_MIN_SERIAL_LEN (6)
+
+/* control messages from userspace */
+#define WCNSS_USR_CTRL_MSG_START 0x00000000
+#define WCNSS_USR_SERIAL_NUM (WCNSS_USR_CTRL_MSG_START + 1)
+#define WCNSS_USR_HAS_CAL_DATA (WCNSS_USR_CTRL_MSG_START + 2)
/* message types */
#define WCNSS_CTRL_MSG_START 0x01000000
@@ -361,7 +370,9 @@
int device_opened;
int iris_xo_mode_set;
int fw_vbatt_state;
+ int ctrl_device_opened;
struct mutex dev_lock;
+ struct mutex ctrl_lock;
wait_queue_head_t read_wait;
struct qpnp_adc_tm_btm_param vbat_monitor_params;
struct qpnp_adc_tm_chip *adc_tm_dev;
@@ -1823,6 +1834,80 @@
.notifier_call = wcnss_pm_notify,
};
+static int wcnss_ctrl_open(struct inode *inode, struct file *file)
+{
+ int rc = 0;
+
+ if (!penv || penv->ctrl_device_opened)
+ return -EFAULT;
+
+ penv->ctrl_device_opened = 1;
+
+ return rc;
+}
+
+
+void process_usr_ctrl_cmd(u8 *buf, size_t len)
+{
+ u16 cmd = buf[0] << 8 | buf[1];
+
+ switch (cmd) {
+
+ case WCNSS_USR_SERIAL_NUM:
+ if (WCNSS_MIN_SERIAL_LEN > len) {
+ pr_err("%s: Invalid serial number\n", __func__);
+ return;
+ }
+ penv->serial_number = buf[2] << 24 | buf[3] << 16
+ | buf[4] << 8 | buf[5];
+ break;
+
+ case WCNSS_USR_HAS_CAL_DATA:
+ if (1 < buf[2])
+ pr_err("%s: Invalid data for cal %d\n", __func__,
+ buf[2]);
+ has_calibrated_data = buf[2];
+ break;
+
+ default:
+ pr_err("%s: Invalid command %d\n", __func__, cmd);
+ break;
+ }
+}
+
+static ssize_t wcnss_ctrl_write(struct file *fp, const char __user
+ *user_buffer, size_t count, loff_t *position)
+{
+ int rc = 0;
+ u8 buf[WCNSS_MAX_CMD_LEN];
+
+ if (!penv || !penv->ctrl_device_opened || WCNSS_MAX_CMD_LEN < count
+ || WCNSS_MIN_CMD_LEN > count)
+ return -EFAULT;
+
+ mutex_lock(&penv->ctrl_lock);
+ rc = copy_from_user(buf, user_buffer, count);
+ if (0 == rc)
+ process_usr_ctrl_cmd(buf, count);
+
+ mutex_unlock(&penv->ctrl_lock);
+
+ return rc;
+}
+
+
+static const struct file_operations wcnss_ctrl_fops = {
+ .owner = THIS_MODULE,
+ .open = wcnss_ctrl_open,
+ .write = wcnss_ctrl_write,
+};
+
+static struct miscdevice wcnss_usr_ctrl = {
+ .minor = MISC_DYNAMIC_MINOR,
+ .name = CTRL_DEVICE,
+ .fops = &wcnss_ctrl_fops,
+};
+
static int
wcnss_trigger_config(struct platform_device *pdev)
{
@@ -2225,6 +2310,7 @@
}
mutex_init(&penv->dev_lock);
+ mutex_init(&penv->ctrl_lock);
mutex_init(&penv->vbat_monitor_mutex);
init_waitqueue_head(&penv->read_wait);
@@ -2237,6 +2323,9 @@
* place
*/
pr_info(DEVICE " probed in built-in mode\n");
+
+ misc_register(&wcnss_usr_ctrl);
+
return misc_register(&wcnss_misc);
}
diff --git a/drivers/video/msm/mdss/mdss_mdp.c b/drivers/video/msm/mdss/mdss_mdp.c
index 3269eec..91c8798 100644
--- a/drivers/video/msm/mdss/mdss_mdp.c
+++ b/drivers/video/msm/mdss/mdss_mdp.c
@@ -546,6 +546,8 @@
if (clk) {
pr_debug("clk=%d en=%d\n", clk_idx, enable);
if (enable) {
+ if (clk_idx == MDSS_CLK_MDP_VSYNC)
+ clk_set_rate(clk, 19200000);
ret = clk_prepare_enable(clk);
} else {
clk_disable_unprepare(clk);
diff --git a/drivers/video/msm/mdss/mdss_mdp.h b/drivers/video/msm/mdss/mdss_mdp.h
index fad6b0c..8918df8 100644
--- a/drivers/video/msm/mdss/mdss_mdp.h
+++ b/drivers/video/msm/mdss/mdss_mdp.h
@@ -274,7 +274,6 @@
u32 hist_cnt_sent;
u32 hist_cnt_time;
u32 frame_cnt;
- u32 is_kick_ready;
struct completion comp;
u32 data[HIST_V_SIZE];
struct mutex hist_mutex;
diff --git a/drivers/video/msm/mdss/mdss_mdp_pp.c b/drivers/video/msm/mdss/mdss_mdp_pp.c
index 28d1b82..88af216 100644
--- a/drivers/video/msm/mdss/mdss_mdp_pp.c
+++ b/drivers/video/msm/mdss/mdss_mdp_pp.c
@@ -1307,10 +1307,7 @@
mutex_lock(&hist_info->hist_mutex);
spin_lock_irqsave(&hist_info->hist_lock, flag);
col_state = hist_info->col_state;
- if (hist_info->is_kick_ready &&
- ((col_state == HIST_IDLE) ||
- ((false == hist_info->read_request) &&
- col_state == HIST_READY))) {
+ if (col_state == HIST_IDLE) {
/* Kick off collection */
writel_relaxed(1, base + kick_base);
hist_info->col_state = HIST_START;
@@ -2893,11 +2890,10 @@
hist_info->hist_cnt_sent = 0;
hist_info->hist_cnt_time = 0;
spin_lock_irqsave(&hist_info->hist_lock, flag);
- hist_info->read_request = false;
+ hist_info->read_request = 0;
hist_info->col_state = HIST_RESET;
hist_info->col_en = true;
spin_unlock_irqrestore(&hist_info->hist_lock, flag);
- hist_info->is_kick_ready = true;
mdss_mdp_hist_intr_req(&mdata->hist_intr, 3 << shift_bit, true);
writel_relaxed(req->frame_cnt, ctl_base + 8);
/* Kick out reset start */
@@ -3018,7 +3014,6 @@
hist_info->col_en = false;
hist_info->col_state = HIST_UNKNOWN;
spin_unlock_irqrestore(&hist_info->hist_lock, flag);
- hist_info->is_kick_ready = false;
mdss_mdp_hist_intr_req(&mdata->hist_intr, done_bit, false);
writel_relaxed(BIT(1), ctl_base);/* cancel */
ret = 0;
@@ -3268,7 +3263,6 @@
spin_lock_irqsave(&hist_info->hist_lock, flag);
/* wait for hist done if cache has no data */
if (hist_info->col_state != HIST_READY) {
- hist_info->read_request = true;
spin_unlock_irqrestore(&hist_info->hist_lock, flag);
timeout = HIST_WAIT_TIMEOUT(hist_info->frame_cnt);
mutex_unlock(&hist_info->hist_mutex);
@@ -3308,9 +3302,11 @@
}
if (hist_info->col_state != HIST_READY) {
ret = -ENODATA;
+ spin_lock_irqsave(&hist_info->hist_lock, flag);
+ hist_info->col_state = HIST_READY;
+ spin_unlock_irqrestore(&hist_info->hist_lock, flag);
pr_debug("%s: state is not ready: %d",
__func__, hist_info->col_state);
- goto hist_collect_exit;
}
} else {
spin_unlock_irqrestore(&hist_info->hist_lock, flag);
@@ -3323,9 +3319,7 @@
sum = pp_hist_read(v_base, hist_info);
mdss_mdp_clk_ctrl(MDP_BLOCK_POWER_OFF, false);
spin_lock_irqsave(&hist_info->hist_lock, flag);
- if (!expect_sum || sum == expect_sum)
- hist_info->read_request = false;
- else
+ if (expect_sum && sum != expect_sum)
ret = -ENODATA;
hist_info->col_state = HIST_IDLE;
}
@@ -3337,8 +3331,9 @@
int mdss_mdp_hist_collect(struct mdp_histogram_data *hist)
{
- int i, j, off, ret = 0;
+ int i, j, off, ret = 0, temp_ret = 0;
struct pp_hist_col_info *hist_info;
+ struct pp_hist_col_info *hists[MDSS_MDP_INTF_MAX_LAYERMIXER];
u32 dspp_num, disp_num;
char __iomem *ctl_base;
u32 hist_cnt, mixer_id[MDSS_MDP_INTF_MAX_LAYERMIXER];
@@ -3349,6 +3344,7 @@
u32 exp_sum = 0;
struct mdss_mdp_pipe *pipe;
struct mdss_data_type *mdata = mdss_mdp_get_mdata();
+ unsigned long flag;
if ((PP_BLOCK(hist->block) < MDP_LOGICAL_BLOCK_DISP_0) ||
(PP_BLOCK(hist->block) >= MDP_BLOCK_MAX))
@@ -3369,20 +3365,41 @@
ret = -EPERM;
goto hist_collect_exit;
}
+
if (PP_LOCAT(hist->block) == MDSS_PP_DSPP_CFG) {
- hist_info = &mdss_pp_res->dspp_hist[disp_num];
for (i = 0; i < hist_cnt; i++) {
dspp_num = mixer_id[i];
- hist_info = &mdss_pp_res->dspp_hist[dspp_num];
+ hists[i] = &mdss_pp_res->dspp_hist[dspp_num];
+ }
+ for (i = 0; i < hist_cnt; i++) {
+ spin_lock_irqsave(&hists[i]->hist_lock, flag);
+ /* mark that collect is ready to handle completions */
+ hists[i]->read_request = 1;
+ spin_unlock_irqrestore(&hists[i]->hist_lock, flag);
+ }
+ for (i = 0; i < hist_cnt; i++) {
+ dspp_num = mixer_id[i];
ctl_base = mdss_mdp_get_dspp_addr_off(dspp_num) +
MDSS_MDP_REG_DSPP_HIST_CTL_BASE;
exp_sum = (mdata->mixer_intf[dspp_num].width *
mdata->mixer_intf[dspp_num].height);
- ret = pp_hist_collect(hist, hist_info, ctl_base,
- exp_sum);
if (ret)
- goto hist_collect_exit;
+ temp_ret = ret;
+ ret = pp_hist_collect(hist, hists[i], ctl_base,
+ exp_sum);
}
+ for (i = 0; i < hist_cnt; i++) {
+ /* reset read requests and re-intialize completions */
+ spin_lock_irqsave(&hists[i]->hist_lock, flag);
+ hists[i]->read_request = 0;
+ INIT_COMPLETION(hists[i]->comp);
+ spin_unlock_irqrestore(&hists[i]->hist_lock, flag);
+ }
+ if (ret || temp_ret) {
+ ret = ret ? ret : temp_ret;
+ goto hist_collect_exit;
+ }
+
if (hist->bin_cnt != HIST_V_SIZE) {
pr_err("User not expecting size %d output",
HIST_V_SIZE);
@@ -3398,19 +3415,19 @@
}
memset(hist_concat, 0, HIST_V_SIZE * sizeof(u32));
for (i = 0; i < hist_cnt; i++) {
- dspp_num = mixer_id[i];
- hist_info = &mdss_pp_res->dspp_hist[dspp_num];
- mutex_lock(&hist_info->hist_mutex);
+ mutex_lock(&hists[i]->hist_mutex);
for (j = 0; j < HIST_V_SIZE; j++)
- hist_concat[j] += hist_info->data[j];
- mutex_unlock(&hist_info->hist_mutex);
+ hist_concat[j] += hists[i]->data[j];
+ mutex_unlock(&hists[i]->hist_mutex);
}
hist_data_addr = hist_concat;
} else {
- hist_data_addr = hist_info->data;
+ hist_data_addr = hists[0]->data;
}
- hist_info = &mdss_pp_res->dspp_hist[disp_num];
- hist_info->hist_cnt_sent++;
+
+ for (i = 0; i < hist_cnt; i++)
+ hists[i]->hist_cnt_sent++;
+
} else if (PP_LOCAT(hist->block) == MDSS_PP_SSPP_CFG) {
hist_cnt = MDSS_PP_ARG_MASK & hist->block;
@@ -3446,14 +3463,50 @@
continue;
}
hist_info = &pipe->pp_res.hist;
+ spin_lock_irqsave(&hist_info->hist_lock, flag);
+ hist_info->read_request = 1;
+ spin_unlock_irqrestore(&hist_info->hist_lock, flag);
+ }
+ for (i = pipe_num; i < MDSS_PP_ARG_NUM; i++) {
+ if (!PP_ARG(i, hist->block))
+ continue;
+ pipe_cnt++;
+ pipe = mdss_mdp_pipe_get(mdata, BIT(i));
+ if (IS_ERR_OR_NULL(pipe) ||
+ pipe->num > MDSS_MDP_SSPP_VIG2) {
+ pr_warn("Invalid Hist pipe (%d)", i);
+ continue;
+ }
+ hist_info = &pipe->pp_res.hist;
ctl_base = pipe->base +
MDSS_MDP_REG_VIG_HIST_CTL_BASE;
+ if (ret)
+ temp_ret = ret;
ret = pp_hist_collect(hist, hist_info, ctl_base,
exp_sum);
mdss_mdp_pipe_unmap(pipe);
- if (ret)
- goto hist_collect_exit;
}
+ for (i = pipe_num; i < MDSS_PP_ARG_NUM; i++) {
+ if (!PP_ARG(i, hist->block))
+ continue;
+ pipe_cnt++;
+ pipe = mdss_mdp_pipe_get(mdata, BIT(i));
+ if (IS_ERR_OR_NULL(pipe) ||
+ pipe->num > MDSS_MDP_SSPP_VIG2) {
+ pr_warn("Invalid Hist pipe (%d)", i);
+ continue;
+ }
+ hist_info = &pipe->pp_res.hist;
+ spin_lock_irqsave(&hist_info->hist_lock, flag);
+ hist_info->read_request = 0;
+ INIT_COMPLETION(hist_info->comp);
+ spin_unlock_irqrestore(&hist_info->hist_lock, flag);
+ }
+ if (ret || temp_ret) {
+ ret = ret ? ret : temp_ret;
+ goto hist_collect_exit;
+ }
+
if (pipe_cnt != 0 &&
(hist->bin_cnt != (HIST_V_SIZE * pipe_cnt))) {
pr_err("User not expecting size %d output",
@@ -3551,8 +3604,10 @@
spin_lock(&hist_info->hist_lock);
hist_info->col_state = HIST_READY;
spin_unlock(&hist_info->hist_lock);
- if (hist_info->read_request)
+ if (hist_info->read_request == 1) {
complete(&hist_info->comp);
+ hist_info->read_request++;
+ }
}
/* Histogram Reset Done Interrupt */
if ((isr_blk & 0x2) &&
@@ -4542,7 +4597,10 @@
pipe = mdss_res->vig_pipes + counter;
base = pipe->base;
- if (ptr == base + MDSS_MDP_REG_SSPP_SRC_FORMAT) {
+ if (ptr == base + MDSS_MDP_REG_VIG_OP_MODE) {
+ ret = MDP_PP_OPS_READ | MDP_PP_OPS_WRITE;
+ break;
+ } else if (ptr == base + MDSS_MDP_REG_SSPP_SRC_FORMAT) {
ret = MDP_PP_OPS_READ | MDP_PP_OPS_WRITE;
break;
} else if (ptr == base + MDSS_MDP_REG_SSPP_SRC_CONSTANT_COLOR) {
@@ -4551,6 +4609,9 @@
} else if (ptr == base + MDSS_MDP_REG_SSPP_SRC_UNPACK_PATTERN) {
ret = MDP_PP_OPS_READ | MDP_PP_OPS_WRITE;
break;
+ } else if (ptr == base + MDSS_MDP_REG_SSPP_SRC_OP_MODE) {
+ ret = MDP_PP_OPS_READ | MDP_PP_OPS_WRITE;
+ break;
} else if ((ptr == base + MDSS_MDP_REG_VIG_QSEED2_SHARP)) {
ret = MDP_PP_OPS_READ | MDP_PP_OPS_WRITE;
break;
@@ -4591,6 +4652,9 @@
} else if (ptr == base + MDSS_MDP_REG_SSPP_SRC_UNPACK_PATTERN) {
ret = MDP_PP_OPS_READ | MDP_PP_OPS_WRITE;
break;
+ } else if (ptr == base + MDSS_MDP_REG_SSPP_SRC_OP_MODE) {
+ ret = MDP_PP_OPS_READ | MDP_PP_OPS_WRITE;
+ break;
/* IGC range */
} else if ((ptr >= base + MDSS_MDP_REG_IGC_RGB_BASE) &&
(ptr <= base + MDSS_MDP_REG_IGC_RGB_BASE +
@@ -4622,6 +4686,9 @@
} else if (ptr == base + MDSS_MDP_REG_SSPP_SRC_UNPACK_PATTERN) {
ret = MDP_PP_OPS_READ | MDP_PP_OPS_WRITE;
break;
+ } else if (ptr == base + MDSS_MDP_REG_SSPP_SRC_OP_MODE) {
+ ret = MDP_PP_OPS_READ | MDP_PP_OPS_WRITE;
+ break;
/* IGC range */
} else if ((ptr >= base + MDSS_MDP_REG_IGC_DMA_BASE) &&
(ptr <= base + MDSS_MDP_REG_IGC_DMA_BASE +
diff --git a/include/linux/vmalloc.h b/include/linux/vmalloc.h
index 7675a5c..500421f 100644
--- a/include/linux/vmalloc.h
+++ b/include/linux/vmalloc.h
@@ -136,6 +136,12 @@
extern __init void vm_area_add_early(struct vm_struct *vm);
extern __init void vm_area_register_early(struct vm_struct *vm, size_t align);
extern __init int vm_area_check_early(struct vm_struct *vm);
+#ifdef CONFIG_ENABLE_VMALLOC_SAVING
+extern void mark_vmalloc_reserved_area(void *addr, unsigned long size);
+#else
+static inline void mark_vmalloc_reserved_area(void *addr, unsigned long size)
+{ };
+#endif
#ifdef CONFIG_SMP
# ifdef CONFIG_MMU
diff --git a/mm/vmalloc.c b/mm/vmalloc.c
index e174693..2e074aa 100644
--- a/mm/vmalloc.c
+++ b/mm/vmalloc.c
@@ -184,36 +184,6 @@
return ret;
}
-#ifdef ENABLE_VMALLOC_SAVING
-int is_vmalloc_addr(const void *x)
-{
- struct rb_node *n;
- struct vmap_area *va;
- int ret = 0;
-
- spin_lock(&vmap_area_lock);
-
- for (n = rb_first(vmap_area_root); n; rb_next(n)) {
- va = rb_entry(n, struct vmap_area, rb_node);
- if (x >= va->va_start && x < va->va_end) {
- ret = 1;
- break;
- }
- }
-
- spin_unlock(&vmap_area_lock);
- return ret;
-}
-#else
-int is_vmalloc_addr(const void *x)
-{
- unsigned long addr = (unsigned long)x;
-
- return addr >= VMALLOC_START && addr < VMALLOC_END;
-}
-#endif
-EXPORT_SYMBOL(is_vmalloc_addr);
-
int is_vmalloc_or_module_addr(const void *x)
{
/*
@@ -302,6 +272,47 @@
static unsigned long vmap_area_pcpu_hole;
+#ifdef CONFIG_ENABLE_VMALLOC_SAVING
+#define POSSIBLE_VMALLOC_START PAGE_OFFSET
+
+#define VMALLOC_BITMAP_SIZE ((VMALLOC_END - PAGE_OFFSET) >> \
+ PAGE_SHIFT)
+#define VMALLOC_TO_BIT(addr) ((addr - PAGE_OFFSET) >> PAGE_SHIFT)
+#define BIT_TO_VMALLOC(i) (PAGE_OFFSET + i * PAGE_SIZE)
+
+DECLARE_BITMAP(possible_areas, VMALLOC_BITMAP_SIZE);
+
+void mark_vmalloc_reserved_area(void *x, unsigned long size)
+{
+ unsigned long addr = (unsigned long)x;
+
+ bitmap_set(possible_areas, VMALLOC_TO_BIT(addr), size >> PAGE_SHIFT);
+}
+
+int is_vmalloc_addr(const void *x)
+{
+ unsigned long addr = (unsigned long)x;
+
+ if (addr < POSSIBLE_VMALLOC_START || addr >= VMALLOC_END)
+ return 0;
+
+ if (test_bit(VMALLOC_TO_BIT(addr), possible_areas))
+ return 0;
+
+ return 1;
+}
+#else
+int is_vmalloc_addr(const void *x)
+{
+ unsigned long addr = (unsigned long)x;
+
+ return addr >= VMALLOC_START && addr < VMALLOC_END;
+}
+#endif
+EXPORT_SYMBOL(is_vmalloc_addr);
+
+
+
static struct vmap_area *__find_vmap_area(unsigned long addr)
{
struct rb_node *n = vmap_area_root.rb_node;