mirror of
git://nv-tegra.nvidia.com/linux-nv-oot.git
synced 2025-12-22 17:25:35 +03:00
kernel: nvidia-oot: Fix Linux KMD coverity defects
Fix INT30-C and INT08-C coverity defects for capture-vi.c and tegracam_ctrls.c. Fix MISSING_LOCK coverity defects for channel.c. JIRA CAMERASW-30788 Change-Id: I6ad218cb9184f09d04d862a4c8f3f6db35db65cf Signed-off-by: Bob Zhang <bozhang@nvidia.com> Reviewed-on: https://git-master.nvidia.com/r/c/linux-nv-oot/+/3275901 Reviewed-by: svcacv <svcacv@nvidia.com> Reviewed-by: Xiaoming Xiang <xxiang@nvidia.com> Reviewed-by: Anubhav Rai <arai@nvidia.com> Reviewed-by: Sumeet Gupta <sumeetg@nvidia.com> GVS: buildbot_gerritrpt <buildbot_gerritrpt@nvidia.com> Reviewed-by: Ankur Pawar <ankurp@nvidia.com>
This commit is contained in:
@@ -1,5 +1,6 @@
|
||||
// SPDX-License-Identifier: GPL-2.0-only
|
||||
// SPDX-FileCopyrightText: Copyright (c) 2017-2025 NVIDIA CORPORATION & AFFILIATES.
|
||||
// All rights reserved.
|
||||
|
||||
/**
|
||||
* @file drivers/media/platform/tegra/camera/fusa-capture/capture-vi.c
|
||||
@@ -1400,14 +1401,24 @@ static uint32_t vi_capture_get_num_progress(
|
||||
struct vi_capture_req *req)
|
||||
{
|
||||
struct vi_capture *capture = chan->capture_data;
|
||||
struct capture_descriptor* desc = (struct capture_descriptor*)
|
||||
(capture->requests.va +
|
||||
req->buffer_index * capture->request_size);
|
||||
struct vi_channel_config* config = &desc->ch_cfg;
|
||||
|
||||
const uint16_t minProgress = 2U;
|
||||
uint16_t numProgress = minProgress;
|
||||
|
||||
struct capture_descriptor *desc;
|
||||
struct vi_channel_config *config;
|
||||
|
||||
unsigned int mul_value = 0;
|
||||
|
||||
if (check_mul_overflow(req->buffer_index, capture->request_size, &mul_value)) {
|
||||
dev_err(chan->dev,
|
||||
"%s:capture descriptor offset failed due to an overflow\n", __func__);
|
||||
return minProgress;
|
||||
}
|
||||
|
||||
desc = (struct capture_descriptor *)(capture->requests.va + mul_value);
|
||||
config = &desc->ch_cfg;
|
||||
|
||||
/* Minimum of two progress fences for PXL_SOF and PXL_EOF */
|
||||
if (config->flush_enable == 0x1UL)
|
||||
{
|
||||
@@ -1433,7 +1444,14 @@ static uint32_t vi_capture_get_num_progress(
|
||||
*/
|
||||
if (((config->frame.frame_y - config->flush_first) % config->flush) == 0U)
|
||||
{
|
||||
numProgress--;
|
||||
if (numProgress < minProgress) {
|
||||
dev_err(chan->dev,
|
||||
"%s:numProgress is less than the minimum value\n",
|
||||
__func__);
|
||||
numProgress = minProgress;
|
||||
} else {
|
||||
numProgress--;
|
||||
}
|
||||
}
|
||||
}
|
||||
return (uint32_t)numProgress;
|
||||
@@ -1446,6 +1464,7 @@ int vi_capture_request(
|
||||
struct vi_capture *capture = chan->capture_data;
|
||||
struct CAPTURE_MSG capture_desc;
|
||||
int err = 0;
|
||||
uint32_t sum_value = 0;
|
||||
|
||||
nv_camera_log(chan->ndev,
|
||||
__arch_counter_get_cntvct(),
|
||||
@@ -1495,7 +1514,12 @@ int vi_capture_request(
|
||||
}
|
||||
|
||||
// Progress syncpoints + 1 for status syncpoint
|
||||
capture->progress_sp.threshold += vi_capture_get_num_progress(chan, req) + 1;
|
||||
if (check_add_overflow(vi_capture_get_num_progress(chan, req), 1U, &sum_value)) {
|
||||
dev_err(chan->dev, "%s: check_sub failed due to an overflow\n", __func__);
|
||||
} else if (check_add_overflow(capture->progress_sp.threshold, sum_value,
|
||||
&capture->progress_sp.threshold)) {
|
||||
dev_err(chan->dev, "%s: procress_sp failed due to an overflow\n", __func__);
|
||||
}
|
||||
|
||||
mutex_unlock(&capture->reset_lock);
|
||||
|
||||
|
||||
@@ -1,8 +1,9 @@
|
||||
// SPDX-License-Identifier: GPL-2.0
|
||||
/*
|
||||
// SPDX-License-Identifier: GPL-2.0-only
|
||||
/* SPDX-FileCopyrightText: Copyright (c) 2017-2025 NVIDIA CORPORATION & AFFILIATES.
|
||||
* All rights reserved.
|
||||
*
|
||||
* tegracam_ctrls - control framework for tegra camera drivers
|
||||
*
|
||||
* Copyright (c) 2017-2024, NVIDIA CORPORATION. All rights reserved.
|
||||
*/
|
||||
|
||||
#include <linux/nospec.h>
|
||||
@@ -899,8 +900,35 @@ static int tegracam_check_ctrl_ops(
|
||||
"ERROR: Can not mix normal and extended sensor controls\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
total_ops = sensor_ops + mode_ops + string_ops + default_ops + compound_ops;
|
||||
total_ops += sensor_ex_ops + default_ex_ops;
|
||||
|
||||
if (check_add_overflow(total_ops, sensor_ops, &total_ops)) {
|
||||
dev_err(dev, "%s:sensor ops failed due to an overflow\n", __func__);
|
||||
return -EINVAL;
|
||||
}
|
||||
if (check_add_overflow(total_ops, mode_ops, &total_ops)) {
|
||||
dev_err(dev, "%s:mode ops failed due to an overflow\n", __func__);
|
||||
return -EINVAL;
|
||||
}
|
||||
if (check_add_overflow(total_ops, string_ops, &total_ops)) {
|
||||
dev_err(dev, "%s:string ops failed due to an overflow\n", __func__);
|
||||
return -EINVAL;
|
||||
}
|
||||
if (check_add_overflow(total_ops, default_ops, &total_ops)) {
|
||||
dev_err(dev, "%s:default ops failed due to an overflow\n", __func__);
|
||||
return -EINVAL;
|
||||
}
|
||||
if (check_add_overflow(total_ops, compound_ops, &total_ops)) {
|
||||
dev_err(dev, "%s:compound ops failed due to an overflow\n", __func__);
|
||||
return -EINVAL;
|
||||
}
|
||||
if (check_add_overflow(total_ops, sensor_ex_ops, &total_ops)) {
|
||||
dev_err(dev, "%s:sensor ex ops failed due to an overflow\n", __func__);
|
||||
return -EINVAL;
|
||||
}
|
||||
if (check_add_overflow(total_ops, default_ex_ops, &total_ops)) {
|
||||
dev_err(dev, "%s:default ex ops failed due to an overflow\n", __func__);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (total_ops != (ops->numctrls + TEGRACAM_DEF_CTRLS)) {
|
||||
dev_err(dev,
|
||||
|
||||
@@ -411,6 +411,7 @@ void release_buffer(struct tegra_channel *chan,
|
||||
{
|
||||
struct vb2_v4l2_buffer *vbuf = &buf->buf;
|
||||
s64 frame_arrived_ts = 0;
|
||||
unsigned long flags;
|
||||
|
||||
/* release one frame */
|
||||
vbuf->sequence = chan->sequence;
|
||||
@@ -423,6 +424,7 @@ void release_buffer(struct tegra_channel *chan,
|
||||
vb2_set_plane_payload(&vbuf->vb2_buf,
|
||||
0, chan->format.sizeimage);
|
||||
|
||||
spin_lock_irqsave(&chan->capture_state_lock, flags);
|
||||
/*
|
||||
* WAR to force buffer state if capture state is not good
|
||||
* WAR - After sync point timeout or error frame capture
|
||||
@@ -431,6 +433,7 @@ void release_buffer(struct tegra_channel *chan,
|
||||
*/
|
||||
if (chan->capture_state != CAPTURE_GOOD || vbuf->sequence < 2)
|
||||
buf->state = VB2_BUF_STATE_ERROR;
|
||||
spin_unlock_irqrestore(&chan->capture_state_lock, flags);
|
||||
|
||||
if (chan->sequence == 1) {
|
||||
/*
|
||||
@@ -507,6 +510,7 @@ void free_ring_buffers(struct tegra_channel *chan, int frames)
|
||||
{
|
||||
struct vb2_v4l2_buffer *vbuf;
|
||||
s64 frame_arrived_ts = 0;
|
||||
unsigned long flags;
|
||||
|
||||
spin_lock(&chan->buffer_lock);
|
||||
|
||||
@@ -529,6 +533,7 @@ void free_ring_buffers(struct tegra_channel *chan, int frames)
|
||||
vb2_set_plane_payload(&vbuf->vb2_buf,
|
||||
0, chan->format.sizeimage);
|
||||
|
||||
spin_lock_irqsave(&chan->capture_state_lock, flags);
|
||||
/*
|
||||
* WAR to force buffer state if capture state is not good
|
||||
* WAR - After sync point timeout or error frame capture
|
||||
@@ -540,6 +545,7 @@ void free_ring_buffers(struct tegra_channel *chan, int frames)
|
||||
chan->released_bufs < 2)
|
||||
chan->buffer_state[chan->free_index] =
|
||||
VB2_BUF_STATE_ERROR;
|
||||
spin_unlock_irqrestore(&chan->capture_state_lock, flags);
|
||||
|
||||
if (chan->sequence == 1) {
|
||||
/*
|
||||
@@ -587,6 +593,7 @@ static void add_buffer_to_ring(struct tegra_channel *chan,
|
||||
static void update_state_to_buffer(struct tegra_channel *chan, int state)
|
||||
{
|
||||
int save_index = ((int)chan->save_index - PREVIOUS_BUFFER_DEC_INDEX);
|
||||
unsigned long flags;
|
||||
|
||||
/* save index decrements by 2 as 3 bufs are added in ring buffer */
|
||||
if (save_index < 0)
|
||||
@@ -594,29 +601,35 @@ static void update_state_to_buffer(struct tegra_channel *chan, int state)
|
||||
/* update state for the previous buffer */
|
||||
chan->buffer_state[save_index] = state;
|
||||
|
||||
spin_lock_irqsave(&chan->capture_state_lock, flags);
|
||||
/* for timeout/error case update the current buffer state as well */
|
||||
if (chan->capture_state != CAPTURE_GOOD)
|
||||
chan->buffer_state[chan->save_index] = state;
|
||||
spin_unlock_irqrestore(&chan->capture_state_lock, flags);
|
||||
}
|
||||
|
||||
void tegra_channel_ring_buffer(struct tegra_channel *chan,
|
||||
struct vb2_v4l2_buffer *vb,
|
||||
struct timespec64 *ts, int state)
|
||||
{
|
||||
unsigned long flags;
|
||||
if (!chan->bfirst_fstart)
|
||||
chan->bfirst_fstart = true;
|
||||
else
|
||||
update_state_to_buffer(chan, state);
|
||||
|
||||
spin_lock_irqsave(&chan->capture_state_lock, flags);
|
||||
/* Capture state is not GOOD, release all buffers and re-init state */
|
||||
if (chan->capture_state != CAPTURE_GOOD) {
|
||||
free_ring_buffers(chan, chan->num_buffers);
|
||||
tegra_channel_init_ring_buffer(chan);
|
||||
spin_unlock_irqrestore(&chan->capture_state_lock, flags);
|
||||
return;
|
||||
} else {
|
||||
/* TODO: granular time code information */
|
||||
vb->timecode.seconds = ts->tv_sec;
|
||||
}
|
||||
spin_unlock_irqrestore(&chan->capture_state_lock, flags);
|
||||
|
||||
/* release buffer N at N+2 frame start event */
|
||||
if (chan->num_buffers >= (chan->capture_queue_depth - 1))
|
||||
|
||||
Reference in New Issue
Block a user