Commit c1cc03ea authored by Laurent Pinchart's avatar Laurent Pinchart Committed by Mauro Carvalho Chehab

media: imx: imx-mipi-csis: Rename csi_state to mipi_csis_device

Usage of "state" for the device-specific data structure is confusing, as
it can also refer to the subdev state. Rename the structure to
mipi_csis_device, and the corresponding state variables to csis.
Signed-off-by: default avatarLaurent Pinchart <laurent.pinchart@ideasonboard.com>
Reviewed-by: default avatarJacopo Mondi <jacopo@jmondi.org>
Signed-off-by: default avatarMauro Carvalho Chehab <mchehab@kernel.org>
parent 309373a3
...@@ -310,7 +310,7 @@ struct mipi_csis_info { ...@@ -310,7 +310,7 @@ struct mipi_csis_info {
unsigned int num_clocks; unsigned int num_clocks;
}; };
struct csi_state { struct mipi_csis_device {
struct device *dev; struct device *dev;
void __iomem *regs; void __iomem *regs;
struct clk_bulk_data *clks; struct clk_bulk_data *clks;
...@@ -515,59 +515,60 @@ static const struct csis_pix_format *find_csis_format(u32 code) ...@@ -515,59 +515,60 @@ static const struct csis_pix_format *find_csis_format(u32 code)
* Hardware configuration * Hardware configuration
*/ */
static inline u32 mipi_csis_read(struct csi_state *state, u32 reg) static inline u32 mipi_csis_read(struct mipi_csis_device *csis, u32 reg)
{ {
return readl(state->regs + reg); return readl(csis->regs + reg);
} }
static inline void mipi_csis_write(struct csi_state *state, u32 reg, u32 val) static inline void mipi_csis_write(struct mipi_csis_device *csis, u32 reg,
u32 val)
{ {
writel(val, state->regs + reg); writel(val, csis->regs + reg);
} }
static void mipi_csis_enable_interrupts(struct csi_state *state, bool on) static void mipi_csis_enable_interrupts(struct mipi_csis_device *csis, bool on)
{ {
mipi_csis_write(state, MIPI_CSIS_INT_MSK, on ? 0xffffffff : 0); mipi_csis_write(csis, MIPI_CSIS_INT_MSK, on ? 0xffffffff : 0);
mipi_csis_write(state, MIPI_CSIS_DBG_INTR_MSK, on ? 0xffffffff : 0); mipi_csis_write(csis, MIPI_CSIS_DBG_INTR_MSK, on ? 0xffffffff : 0);
} }
static void mipi_csis_sw_reset(struct csi_state *state) static void mipi_csis_sw_reset(struct mipi_csis_device *csis)
{ {
u32 val = mipi_csis_read(state, MIPI_CSIS_CMN_CTRL); u32 val = mipi_csis_read(csis, MIPI_CSIS_CMN_CTRL);
mipi_csis_write(state, MIPI_CSIS_CMN_CTRL, mipi_csis_write(csis, MIPI_CSIS_CMN_CTRL,
val | MIPI_CSIS_CMN_CTRL_RESET); val | MIPI_CSIS_CMN_CTRL_RESET);
usleep_range(10, 20); usleep_range(10, 20);
} }
static void mipi_csis_system_enable(struct csi_state *state, int on) static void mipi_csis_system_enable(struct mipi_csis_device *csis, int on)
{ {
u32 val, mask; u32 val, mask;
val = mipi_csis_read(state, MIPI_CSIS_CMN_CTRL); val = mipi_csis_read(csis, MIPI_CSIS_CMN_CTRL);
if (on) if (on)
val |= MIPI_CSIS_CMN_CTRL_ENABLE; val |= MIPI_CSIS_CMN_CTRL_ENABLE;
else else
val &= ~MIPI_CSIS_CMN_CTRL_ENABLE; val &= ~MIPI_CSIS_CMN_CTRL_ENABLE;
mipi_csis_write(state, MIPI_CSIS_CMN_CTRL, val); mipi_csis_write(csis, MIPI_CSIS_CMN_CTRL, val);
val = mipi_csis_read(state, MIPI_CSIS_DPHY_CMN_CTRL); val = mipi_csis_read(csis, MIPI_CSIS_DPHY_CMN_CTRL);
val &= ~MIPI_CSIS_DPHY_CMN_CTRL_ENABLE; val &= ~MIPI_CSIS_DPHY_CMN_CTRL_ENABLE;
if (on) { if (on) {
mask = (1 << (state->bus.num_data_lanes + 1)) - 1; mask = (1 << (csis->bus.num_data_lanes + 1)) - 1;
val |= (mask & MIPI_CSIS_DPHY_CMN_CTRL_ENABLE); val |= (mask & MIPI_CSIS_DPHY_CMN_CTRL_ENABLE);
} }
mipi_csis_write(state, MIPI_CSIS_DPHY_CMN_CTRL, val); mipi_csis_write(csis, MIPI_CSIS_DPHY_CMN_CTRL, val);
} }
/* Called with the state.lock mutex held */ /* Called with the csis.lock mutex held */
static void __mipi_csis_set_format(struct csi_state *state) static void __mipi_csis_set_format(struct mipi_csis_device *csis)
{ {
struct v4l2_mbus_framefmt *mf = &state->format_mbus[CSIS_PAD_SINK]; struct v4l2_mbus_framefmt *mf = &csis->format_mbus[CSIS_PAD_SINK];
u32 val; u32 val;
/* Color format */ /* Color format */
val = mipi_csis_read(state, MIPI_CSIS_ISP_CONFIG_CH(0)); val = mipi_csis_read(csis, MIPI_CSIS_ISP_CONFIG_CH(0));
val &= ~(MIPI_CSIS_ISPCFG_ALIGN_32BIT | MIPI_CSIS_ISPCFG_FMT_MASK val &= ~(MIPI_CSIS_ISPCFG_ALIGN_32BIT | MIPI_CSIS_ISPCFG_FMT_MASK
| MIPI_CSIS_ISPCFG_PIXEL_MASK); | MIPI_CSIS_ISPCFG_PIXEL_MASK);
...@@ -584,28 +585,28 @@ static void __mipi_csis_set_format(struct csi_state *state) ...@@ -584,28 +585,28 @@ static void __mipi_csis_set_format(struct csi_state *state)
* *
* TODO: Verify which other formats require DUAL (or QUAD) modes. * TODO: Verify which other formats require DUAL (or QUAD) modes.
*/ */
if (state->csis_fmt->data_type == MIPI_CSI2_DATA_TYPE_YUV422_8) if (csis->csis_fmt->data_type == MIPI_CSI2_DATA_TYPE_YUV422_8)
val |= MIPI_CSIS_ISPCFG_PIXEL_MODE_DUAL; val |= MIPI_CSIS_ISPCFG_PIXEL_MODE_DUAL;
val |= MIPI_CSIS_ISPCFG_FMT(state->csis_fmt->data_type); val |= MIPI_CSIS_ISPCFG_FMT(csis->csis_fmt->data_type);
mipi_csis_write(state, MIPI_CSIS_ISP_CONFIG_CH(0), val); mipi_csis_write(csis, MIPI_CSIS_ISP_CONFIG_CH(0), val);
/* Pixel resolution */ /* Pixel resolution */
val = mf->width | (mf->height << 16); val = mf->width | (mf->height << 16);
mipi_csis_write(state, MIPI_CSIS_ISP_RESOL_CH(0), val); mipi_csis_write(csis, MIPI_CSIS_ISP_RESOL_CH(0), val);
} }
static int mipi_csis_calculate_params(struct csi_state *state) static int mipi_csis_calculate_params(struct mipi_csis_device *csis)
{ {
s64 link_freq; s64 link_freq;
u32 lane_rate; u32 lane_rate;
/* Calculate the line rate from the pixel rate. */ /* Calculate the line rate from the pixel rate. */
link_freq = v4l2_get_link_freq(state->src_sd->ctrl_handler, link_freq = v4l2_get_link_freq(csis->src_sd->ctrl_handler,
state->csis_fmt->width, csis->csis_fmt->width,
state->bus.num_data_lanes * 2); csis->bus.num_data_lanes * 2);
if (link_freq < 0) { if (link_freq < 0) {
dev_err(state->dev, "Unable to obtain link frequency: %d\n", dev_err(csis->dev, "Unable to obtain link frequency: %d\n",
(int)link_freq); (int)link_freq);
return link_freq; return link_freq;
} }
...@@ -613,7 +614,7 @@ static int mipi_csis_calculate_params(struct csi_state *state) ...@@ -613,7 +614,7 @@ static int mipi_csis_calculate_params(struct csi_state *state)
lane_rate = link_freq * 2; lane_rate = link_freq * 2;
if (lane_rate < 80000000 || lane_rate > 1500000000) { if (lane_rate < 80000000 || lane_rate > 1500000000) {
dev_dbg(state->dev, "Out-of-bound lane rate %u\n", lane_rate); dev_dbg(csis->dev, "Out-of-bound lane rate %u\n", lane_rate);
return -EINVAL; return -EINVAL;
} }
...@@ -623,57 +624,57 @@ static int mipi_csis_calculate_params(struct csi_state *state) ...@@ -623,57 +624,57 @@ static int mipi_csis_calculate_params(struct csi_state *state)
* (which is documented as corresponding to CSI-2 v0.87 to v1.00) until * (which is documented as corresponding to CSI-2 v0.87 to v1.00) until
* we figure out how to compute it correctly. * we figure out how to compute it correctly.
*/ */
state->hs_settle = (lane_rate - 5000000) / 45000000; csis->hs_settle = (lane_rate - 5000000) / 45000000;
state->clk_settle = 0; csis->clk_settle = 0;
dev_dbg(state->dev, "lane rate %u, Tclk_settle %u, Ths_settle %u\n", dev_dbg(csis->dev, "lane rate %u, Tclk_settle %u, Ths_settle %u\n",
lane_rate, state->clk_settle, state->hs_settle); lane_rate, csis->clk_settle, csis->hs_settle);
if (state->debug.hs_settle < 0xff) { if (csis->debug.hs_settle < 0xff) {
dev_dbg(state->dev, "overriding Ths_settle with %u\n", dev_dbg(csis->dev, "overriding Ths_settle with %u\n",
state->debug.hs_settle); csis->debug.hs_settle);
state->hs_settle = state->debug.hs_settle; csis->hs_settle = csis->debug.hs_settle;
} }
if (state->debug.clk_settle < 4) { if (csis->debug.clk_settle < 4) {
dev_dbg(state->dev, "overriding Tclk_settle with %u\n", dev_dbg(csis->dev, "overriding Tclk_settle with %u\n",
state->debug.clk_settle); csis->debug.clk_settle);
state->clk_settle = state->debug.clk_settle; csis->clk_settle = csis->debug.clk_settle;
} }
return 0; return 0;
} }
static void mipi_csis_set_params(struct csi_state *state) static void mipi_csis_set_params(struct mipi_csis_device *csis)
{ {
int lanes = state->bus.num_data_lanes; int lanes = csis->bus.num_data_lanes;
u32 val; u32 val;
val = mipi_csis_read(state, MIPI_CSIS_CMN_CTRL); val = mipi_csis_read(csis, MIPI_CSIS_CMN_CTRL);
val &= ~MIPI_CSIS_CMN_CTRL_LANE_NR_MASK; val &= ~MIPI_CSIS_CMN_CTRL_LANE_NR_MASK;
val |= (lanes - 1) << MIPI_CSIS_CMN_CTRL_LANE_NR_OFFSET; val |= (lanes - 1) << MIPI_CSIS_CMN_CTRL_LANE_NR_OFFSET;
if (state->info->version == MIPI_CSIS_V3_3) if (csis->info->version == MIPI_CSIS_V3_3)
val |= MIPI_CSIS_CMN_CTRL_INTER_MODE; val |= MIPI_CSIS_CMN_CTRL_INTER_MODE;
mipi_csis_write(state, MIPI_CSIS_CMN_CTRL, val); mipi_csis_write(csis, MIPI_CSIS_CMN_CTRL, val);
__mipi_csis_set_format(state); __mipi_csis_set_format(csis);
mipi_csis_write(state, MIPI_CSIS_DPHY_CMN_CTRL, mipi_csis_write(csis, MIPI_CSIS_DPHY_CMN_CTRL,
MIPI_CSIS_DPHY_CMN_CTRL_HSSETTLE(state->hs_settle) | MIPI_CSIS_DPHY_CMN_CTRL_HSSETTLE(csis->hs_settle) |
MIPI_CSIS_DPHY_CMN_CTRL_CLKSETTLE(state->clk_settle)); MIPI_CSIS_DPHY_CMN_CTRL_CLKSETTLE(csis->clk_settle));
val = (0 << MIPI_CSIS_ISP_SYNC_HSYNC_LINTV_OFFSET) val = (0 << MIPI_CSIS_ISP_SYNC_HSYNC_LINTV_OFFSET)
| (0 << MIPI_CSIS_ISP_SYNC_VSYNC_SINTV_OFFSET) | (0 << MIPI_CSIS_ISP_SYNC_VSYNC_SINTV_OFFSET)
| (0 << MIPI_CSIS_ISP_SYNC_VSYNC_EINTV_OFFSET); | (0 << MIPI_CSIS_ISP_SYNC_VSYNC_EINTV_OFFSET);
mipi_csis_write(state, MIPI_CSIS_ISP_SYNC_CH(0), val); mipi_csis_write(csis, MIPI_CSIS_ISP_SYNC_CH(0), val);
val = mipi_csis_read(state, MIPI_CSIS_CLK_CTRL); val = mipi_csis_read(csis, MIPI_CSIS_CLK_CTRL);
val |= MIPI_CSIS_CLK_CTRL_WCLK_SRC; val |= MIPI_CSIS_CLK_CTRL_WCLK_SRC;
val |= MIPI_CSIS_CLK_CTRL_CLKGATE_TRAIL_CH0(15); val |= MIPI_CSIS_CLK_CTRL_CLKGATE_TRAIL_CH0(15);
val &= ~MIPI_CSIS_CLK_CTRL_CLKGATE_EN_MSK; val &= ~MIPI_CSIS_CLK_CTRL_CLKGATE_EN_MSK;
mipi_csis_write(state, MIPI_CSIS_CLK_CTRL, val); mipi_csis_write(csis, MIPI_CSIS_CLK_CTRL, val);
mipi_csis_write(state, MIPI_CSIS_DPHY_BCTRL_L, mipi_csis_write(csis, MIPI_CSIS_DPHY_BCTRL_L,
MIPI_CSIS_DPHY_BCTRL_L_BIAS_REF_VOLT_715MV | MIPI_CSIS_DPHY_BCTRL_L_BIAS_REF_VOLT_715MV |
MIPI_CSIS_DPHY_BCTRL_L_BGR_CHOPPER_FREQ_3MHZ | MIPI_CSIS_DPHY_BCTRL_L_BGR_CHOPPER_FREQ_3MHZ |
MIPI_CSIS_DPHY_BCTRL_L_REG_12P_LVL_CTL_1_2V | MIPI_CSIS_DPHY_BCTRL_L_REG_12P_LVL_CTL_1_2V |
...@@ -681,95 +682,95 @@ static void mipi_csis_set_params(struct csi_state *state) ...@@ -681,95 +682,95 @@ static void mipi_csis_set_params(struct csi_state *state)
MIPI_CSIS_DPHY_BCTRL_L_LP_RX_VREF_LVL_715MV | MIPI_CSIS_DPHY_BCTRL_L_LP_RX_VREF_LVL_715MV |
MIPI_CSIS_DPHY_BCTRL_L_LP_CD_HYS_60MV | MIPI_CSIS_DPHY_BCTRL_L_LP_CD_HYS_60MV |
MIPI_CSIS_DPHY_BCTRL_L_B_DPHYCTRL(20000000)); MIPI_CSIS_DPHY_BCTRL_L_B_DPHYCTRL(20000000));
mipi_csis_write(state, MIPI_CSIS_DPHY_BCTRL_H, 0); mipi_csis_write(csis, MIPI_CSIS_DPHY_BCTRL_H, 0);
/* Update the shadow register. */ /* Update the shadow register. */
val = mipi_csis_read(state, MIPI_CSIS_CMN_CTRL); val = mipi_csis_read(csis, MIPI_CSIS_CMN_CTRL);
mipi_csis_write(state, MIPI_CSIS_CMN_CTRL, mipi_csis_write(csis, MIPI_CSIS_CMN_CTRL,
val | MIPI_CSIS_CMN_CTRL_UPDATE_SHADOW | val | MIPI_CSIS_CMN_CTRL_UPDATE_SHADOW |
MIPI_CSIS_CMN_CTRL_UPDATE_SHADOW_CTRL); MIPI_CSIS_CMN_CTRL_UPDATE_SHADOW_CTRL);
} }
static int mipi_csis_clk_enable(struct csi_state *state) static int mipi_csis_clk_enable(struct mipi_csis_device *csis)
{ {
return clk_bulk_prepare_enable(state->info->num_clocks, state->clks); return clk_bulk_prepare_enable(csis->info->num_clocks, csis->clks);
} }
static void mipi_csis_clk_disable(struct csi_state *state) static void mipi_csis_clk_disable(struct mipi_csis_device *csis)
{ {
clk_bulk_disable_unprepare(state->info->num_clocks, state->clks); clk_bulk_disable_unprepare(csis->info->num_clocks, csis->clks);
} }
static int mipi_csis_clk_get(struct csi_state *state) static int mipi_csis_clk_get(struct mipi_csis_device *csis)
{ {
unsigned int i; unsigned int i;
int ret; int ret;
state->clks = devm_kcalloc(state->dev, state->info->num_clocks, csis->clks = devm_kcalloc(csis->dev, csis->info->num_clocks,
sizeof(*state->clks), GFP_KERNEL); sizeof(*csis->clks), GFP_KERNEL);
if (!state->clks) if (!csis->clks)
return -ENOMEM; return -ENOMEM;
for (i = 0; i < state->info->num_clocks; i++) for (i = 0; i < csis->info->num_clocks; i++)
state->clks[i].id = mipi_csis_clk_id[i]; csis->clks[i].id = mipi_csis_clk_id[i];
ret = devm_clk_bulk_get(state->dev, state->info->num_clocks, ret = devm_clk_bulk_get(csis->dev, csis->info->num_clocks,
state->clks); csis->clks);
if (ret < 0) if (ret < 0)
return ret; return ret;
/* Set clock rate */ /* Set clock rate */
ret = clk_set_rate(state->clks[MIPI_CSIS_CLK_WRAP].clk, ret = clk_set_rate(csis->clks[MIPI_CSIS_CLK_WRAP].clk,
state->clk_frequency); csis->clk_frequency);
if (ret < 0) if (ret < 0)
dev_err(state->dev, "set rate=%d failed: %d\n", dev_err(csis->dev, "set rate=%d failed: %d\n",
state->clk_frequency, ret); csis->clk_frequency, ret);
return ret; return ret;
} }
static void mipi_csis_start_stream(struct csi_state *state) static void mipi_csis_start_stream(struct mipi_csis_device *csis)
{ {
mipi_csis_sw_reset(state); mipi_csis_sw_reset(csis);
mipi_csis_set_params(state); mipi_csis_set_params(csis);
mipi_csis_system_enable(state, true); mipi_csis_system_enable(csis, true);
mipi_csis_enable_interrupts(state, true); mipi_csis_enable_interrupts(csis, true);
} }
static void mipi_csis_stop_stream(struct csi_state *state) static void mipi_csis_stop_stream(struct mipi_csis_device *csis)
{ {
mipi_csis_enable_interrupts(state, false); mipi_csis_enable_interrupts(csis, false);
mipi_csis_system_enable(state, false); mipi_csis_system_enable(csis, false);
} }
static irqreturn_t mipi_csis_irq_handler(int irq, void *dev_id) static irqreturn_t mipi_csis_irq_handler(int irq, void *dev_id)
{ {
struct csi_state *state = dev_id; struct mipi_csis_device *csis = dev_id;
unsigned long flags; unsigned long flags;
unsigned int i; unsigned int i;
u32 status; u32 status;
u32 dbg_status; u32 dbg_status;
status = mipi_csis_read(state, MIPI_CSIS_INT_SRC); status = mipi_csis_read(csis, MIPI_CSIS_INT_SRC);
dbg_status = mipi_csis_read(state, MIPI_CSIS_DBG_INTR_SRC); dbg_status = mipi_csis_read(csis, MIPI_CSIS_DBG_INTR_SRC);
spin_lock_irqsave(&state->slock, flags); spin_lock_irqsave(&csis->slock, flags);
/* Update the event/error counters */ /* Update the event/error counters */
if ((status & MIPI_CSIS_INT_SRC_ERRORS) || state->debug.enable) { if ((status & MIPI_CSIS_INT_SRC_ERRORS) || csis->debug.enable) {
for (i = 0; i < MIPI_CSIS_NUM_EVENTS; i++) { for (i = 0; i < MIPI_CSIS_NUM_EVENTS; i++) {
struct mipi_csis_event *event = &state->events[i]; struct mipi_csis_event *event = &csis->events[i];
if ((!event->debug && (status & event->mask)) || if ((!event->debug && (status & event->mask)) ||
(event->debug && (dbg_status & event->mask))) (event->debug && (dbg_status & event->mask)))
event->counter++; event->counter++;
} }
} }
spin_unlock_irqrestore(&state->slock, flags); spin_unlock_irqrestore(&csis->slock, flags);
mipi_csis_write(state, MIPI_CSIS_INT_SRC, status); mipi_csis_write(csis, MIPI_CSIS_INT_SRC, status);
mipi_csis_write(state, MIPI_CSIS_DBG_INTR_SRC, dbg_status); mipi_csis_write(csis, MIPI_CSIS_DBG_INTR_SRC, dbg_status);
return IRQ_HANDLED; return IRQ_HANDLED;
} }
...@@ -778,47 +779,47 @@ static irqreturn_t mipi_csis_irq_handler(int irq, void *dev_id) ...@@ -778,47 +779,47 @@ static irqreturn_t mipi_csis_irq_handler(int irq, void *dev_id)
* PHY regulator and reset * PHY regulator and reset
*/ */
static int mipi_csis_phy_enable(struct csi_state *state) static int mipi_csis_phy_enable(struct mipi_csis_device *csis)
{ {
if (state->info->version != MIPI_CSIS_V3_3) if (csis->info->version != MIPI_CSIS_V3_3)
return 0; return 0;
return regulator_enable(state->mipi_phy_regulator); return regulator_enable(csis->mipi_phy_regulator);
} }
static int mipi_csis_phy_disable(struct csi_state *state) static int mipi_csis_phy_disable(struct mipi_csis_device *csis)
{ {
if (state->info->version != MIPI_CSIS_V3_3) if (csis->info->version != MIPI_CSIS_V3_3)
return 0; return 0;
return regulator_disable(state->mipi_phy_regulator); return regulator_disable(csis->mipi_phy_regulator);
} }
static void mipi_csis_phy_reset(struct csi_state *state) static void mipi_csis_phy_reset(struct mipi_csis_device *csis)
{ {
if (state->info->version != MIPI_CSIS_V3_3) if (csis->info->version != MIPI_CSIS_V3_3)
return; return;
reset_control_assert(state->mrst); reset_control_assert(csis->mrst);
msleep(20); msleep(20);
reset_control_deassert(state->mrst); reset_control_deassert(csis->mrst);
} }
static int mipi_csis_phy_init(struct csi_state *state) static int mipi_csis_phy_init(struct mipi_csis_device *csis)
{ {
if (state->info->version != MIPI_CSIS_V3_3) if (csis->info->version != MIPI_CSIS_V3_3)
return 0; return 0;
/* Get MIPI PHY reset and regulator. */ /* Get MIPI PHY reset and regulator. */
state->mrst = devm_reset_control_get_exclusive(state->dev, NULL); csis->mrst = devm_reset_control_get_exclusive(csis->dev, NULL);
if (IS_ERR(state->mrst)) if (IS_ERR(csis->mrst))
return PTR_ERR(state->mrst); return PTR_ERR(csis->mrst);
state->mipi_phy_regulator = devm_regulator_get(state->dev, "phy"); csis->mipi_phy_regulator = devm_regulator_get(csis->dev, "phy");
if (IS_ERR(state->mipi_phy_regulator)) if (IS_ERR(csis->mipi_phy_regulator))
return PTR_ERR(state->mipi_phy_regulator); return PTR_ERR(csis->mipi_phy_regulator);
return regulator_set_voltage(state->mipi_phy_regulator, 1000000, return regulator_set_voltage(csis->mipi_phy_regulator, 1000000,
1000000); 1000000);
} }
...@@ -826,36 +827,36 @@ static int mipi_csis_phy_init(struct csi_state *state) ...@@ -826,36 +827,36 @@ static int mipi_csis_phy_init(struct csi_state *state)
* Debug * Debug
*/ */
static void mipi_csis_clear_counters(struct csi_state *state) static void mipi_csis_clear_counters(struct mipi_csis_device *csis)
{ {
unsigned long flags; unsigned long flags;
unsigned int i; unsigned int i;
spin_lock_irqsave(&state->slock, flags); spin_lock_irqsave(&csis->slock, flags);
for (i = 0; i < MIPI_CSIS_NUM_EVENTS; i++) for (i = 0; i < MIPI_CSIS_NUM_EVENTS; i++)
state->events[i].counter = 0; csis->events[i].counter = 0;
spin_unlock_irqrestore(&state->slock, flags); spin_unlock_irqrestore(&csis->slock, flags);
} }
static void mipi_csis_log_counters(struct csi_state *state, bool non_errors) static void mipi_csis_log_counters(struct mipi_csis_device *csis, bool non_errors)
{ {
unsigned int num_events = non_errors ? MIPI_CSIS_NUM_EVENTS unsigned int num_events = non_errors ? MIPI_CSIS_NUM_EVENTS
: MIPI_CSIS_NUM_EVENTS - 8; : MIPI_CSIS_NUM_EVENTS - 8;
unsigned long flags; unsigned long flags;
unsigned int i; unsigned int i;
spin_lock_irqsave(&state->slock, flags); spin_lock_irqsave(&csis->slock, flags);
for (i = 0; i < num_events; ++i) { for (i = 0; i < num_events; ++i) {
if (state->events[i].counter > 0 || state->debug.enable) if (csis->events[i].counter > 0 || csis->debug.enable)
dev_info(state->dev, "%s events: %d\n", dev_info(csis->dev, "%s events: %d\n",
state->events[i].name, csis->events[i].name,
state->events[i].counter); csis->events[i].counter);
} }
spin_unlock_irqrestore(&state->slock, flags); spin_unlock_irqrestore(&csis->slock, flags);
} }
static int mipi_csis_dump_regs(struct csi_state *state) static int mipi_csis_dump_regs(struct mipi_csis_device *csis)
{ {
static const struct { static const struct {
u32 offset; u32 offset;
...@@ -879,11 +880,11 @@ static int mipi_csis_dump_regs(struct csi_state *state) ...@@ -879,11 +880,11 @@ static int mipi_csis_dump_regs(struct csi_state *state)
unsigned int i; unsigned int i;
u32 cfg; u32 cfg;
dev_info(state->dev, "--- REGISTERS ---\n"); dev_info(csis->dev, "--- REGISTERS ---\n");
for (i = 0; i < ARRAY_SIZE(registers); i++) { for (i = 0; i < ARRAY_SIZE(registers); i++) {
cfg = mipi_csis_read(state, registers[i].offset); cfg = mipi_csis_read(csis, registers[i].offset);
dev_info(state->dev, "%14s: 0x%08x\n", registers[i].name, cfg); dev_info(csis->dev, "%14s: 0x%08x\n", registers[i].name, cfg);
} }
return 0; return 0;
...@@ -891,123 +892,123 @@ static int mipi_csis_dump_regs(struct csi_state *state) ...@@ -891,123 +892,123 @@ static int mipi_csis_dump_regs(struct csi_state *state)
static int mipi_csis_dump_regs_show(struct seq_file *m, void *private) static int mipi_csis_dump_regs_show(struct seq_file *m, void *private)
{ {
struct csi_state *state = m->private; struct mipi_csis_device *csis = m->private;
return mipi_csis_dump_regs(state); return mipi_csis_dump_regs(csis);
} }
DEFINE_SHOW_ATTRIBUTE(mipi_csis_dump_regs); DEFINE_SHOW_ATTRIBUTE(mipi_csis_dump_regs);
static void mipi_csis_debugfs_init(struct csi_state *state) static void mipi_csis_debugfs_init(struct mipi_csis_device *csis)
{ {
state->debug.hs_settle = UINT_MAX; csis->debug.hs_settle = UINT_MAX;
state->debug.clk_settle = UINT_MAX; csis->debug.clk_settle = UINT_MAX;
state->debugfs_root = debugfs_create_dir(dev_name(state->dev), NULL); csis->debugfs_root = debugfs_create_dir(dev_name(csis->dev), NULL);
debugfs_create_bool("debug_enable", 0600, state->debugfs_root, debugfs_create_bool("debug_enable", 0600, csis->debugfs_root,
&state->debug.enable); &csis->debug.enable);
debugfs_create_file("dump_regs", 0600, state->debugfs_root, state, debugfs_create_file("dump_regs", 0600, csis->debugfs_root, csis,
&mipi_csis_dump_regs_fops); &mipi_csis_dump_regs_fops);
debugfs_create_u32("tclk_settle", 0600, state->debugfs_root, debugfs_create_u32("tclk_settle", 0600, csis->debugfs_root,
&state->debug.clk_settle); &csis->debug.clk_settle);
debugfs_create_u32("ths_settle", 0600, state->debugfs_root, debugfs_create_u32("ths_settle", 0600, csis->debugfs_root,
&state->debug.hs_settle); &csis->debug.hs_settle);
} }
static void mipi_csis_debugfs_exit(struct csi_state *state) static void mipi_csis_debugfs_exit(struct mipi_csis_device *csis)
{ {
debugfs_remove_recursive(state->debugfs_root); debugfs_remove_recursive(csis->debugfs_root);
} }
/* ----------------------------------------------------------------------------- /* -----------------------------------------------------------------------------
* V4L2 subdev operations * V4L2 subdev operations
*/ */
static struct csi_state *mipi_sd_to_csis_state(struct v4l2_subdev *sdev) static struct mipi_csis_device *sd_to_mipi_csis_device(struct v4l2_subdev *sdev)
{ {
return container_of(sdev, struct csi_state, sd); return container_of(sdev, struct mipi_csis_device, sd);
} }
static int mipi_csis_s_stream(struct v4l2_subdev *sd, int enable) static int mipi_csis_s_stream(struct v4l2_subdev *sd, int enable)
{ {
struct csi_state *state = mipi_sd_to_csis_state(sd); struct mipi_csis_device *csis = sd_to_mipi_csis_device(sd);
int ret; int ret;
if (enable) { if (enable) {
ret = mipi_csis_calculate_params(state); ret = mipi_csis_calculate_params(csis);
if (ret < 0) if (ret < 0)
return ret; return ret;
mipi_csis_clear_counters(state); mipi_csis_clear_counters(csis);
ret = pm_runtime_resume_and_get(state->dev); ret = pm_runtime_resume_and_get(csis->dev);
if (ret < 0) if (ret < 0)
return ret; return ret;
ret = v4l2_subdev_call(state->src_sd, core, s_power, 1); ret = v4l2_subdev_call(csis->src_sd, core, s_power, 1);
if (ret < 0 && ret != -ENOIOCTLCMD) if (ret < 0 && ret != -ENOIOCTLCMD)
goto done; goto done;
} }
mutex_lock(&state->lock); mutex_lock(&csis->lock);
if (enable) { if (enable) {
if (state->state & ST_SUSPENDED) { if (csis->state & ST_SUSPENDED) {
ret = -EBUSY; ret = -EBUSY;
goto unlock; goto unlock;
} }
mipi_csis_start_stream(state); mipi_csis_start_stream(csis);
ret = v4l2_subdev_call(state->src_sd, video, s_stream, 1); ret = v4l2_subdev_call(csis->src_sd, video, s_stream, 1);
if (ret < 0) if (ret < 0)
goto unlock; goto unlock;
mipi_csis_log_counters(state, true); mipi_csis_log_counters(csis, true);
state->state |= ST_STREAMING; csis->state |= ST_STREAMING;
} else { } else {
v4l2_subdev_call(state->src_sd, video, s_stream, 0); v4l2_subdev_call(csis->src_sd, video, s_stream, 0);
ret = v4l2_subdev_call(state->src_sd, core, s_power, 0); ret = v4l2_subdev_call(csis->src_sd, core, s_power, 0);
if (ret == -ENOIOCTLCMD) if (ret == -ENOIOCTLCMD)
ret = 0; ret = 0;
mipi_csis_stop_stream(state); mipi_csis_stop_stream(csis);
state->state &= ~ST_STREAMING; csis->state &= ~ST_STREAMING;
if (state->debug.enable) if (csis->debug.enable)
mipi_csis_log_counters(state, true); mipi_csis_log_counters(csis, true);
} }
unlock: unlock:
mutex_unlock(&state->lock); mutex_unlock(&csis->lock);
done: done:
if (!enable || ret < 0) if (!enable || ret < 0)
pm_runtime_put(state->dev); pm_runtime_put(csis->dev);
return ret; return ret;
} }
static struct v4l2_mbus_framefmt * static struct v4l2_mbus_framefmt *
mipi_csis_get_format(struct csi_state *state, mipi_csis_get_format(struct mipi_csis_device *csis,
struct v4l2_subdev_state *sd_state, struct v4l2_subdev_state *sd_state,
enum v4l2_subdev_format_whence which, enum v4l2_subdev_format_whence which,
unsigned int pad) unsigned int pad)
{ {
if (which == V4L2_SUBDEV_FORMAT_TRY) if (which == V4L2_SUBDEV_FORMAT_TRY)
return v4l2_subdev_get_try_format(&state->sd, sd_state, pad); return v4l2_subdev_get_try_format(&csis->sd, sd_state, pad);
return &state->format_mbus[pad]; return &csis->format_mbus[pad];
} }
static int mipi_csis_init_cfg(struct v4l2_subdev *sd, static int mipi_csis_init_cfg(struct v4l2_subdev *sd,
struct v4l2_subdev_state *sd_state) struct v4l2_subdev_state *sd_state)
{ {
struct csi_state *state = mipi_sd_to_csis_state(sd); struct mipi_csis_device *csis = sd_to_mipi_csis_device(sd);
struct v4l2_mbus_framefmt *fmt_sink; struct v4l2_mbus_framefmt *fmt_sink;
struct v4l2_mbus_framefmt *fmt_source; struct v4l2_mbus_framefmt *fmt_source;
enum v4l2_subdev_format_whence which; enum v4l2_subdev_format_whence which;
which = sd_state ? V4L2_SUBDEV_FORMAT_TRY : V4L2_SUBDEV_FORMAT_ACTIVE; which = sd_state ? V4L2_SUBDEV_FORMAT_TRY : V4L2_SUBDEV_FORMAT_ACTIVE;
fmt_sink = mipi_csis_get_format(state, sd_state, which, CSIS_PAD_SINK); fmt_sink = mipi_csis_get_format(csis, sd_state, which, CSIS_PAD_SINK);
fmt_sink->code = MEDIA_BUS_FMT_UYVY8_1X16; fmt_sink->code = MEDIA_BUS_FMT_UYVY8_1X16;
fmt_sink->width = MIPI_CSIS_DEF_PIX_WIDTH; fmt_sink->width = MIPI_CSIS_DEF_PIX_WIDTH;
...@@ -1029,7 +1030,7 @@ static int mipi_csis_init_cfg(struct v4l2_subdev *sd, ...@@ -1029,7 +1030,7 @@ static int mipi_csis_init_cfg(struct v4l2_subdev *sd,
if (!sd_state) if (!sd_state)
return 0; return 0;
fmt_source = mipi_csis_get_format(state, sd_state, which, fmt_source = mipi_csis_get_format(csis, sd_state, which,
CSIS_PAD_SOURCE); CSIS_PAD_SOURCE);
*fmt_source = *fmt_sink; *fmt_source = *fmt_sink;
...@@ -1040,15 +1041,15 @@ static int mipi_csis_get_fmt(struct v4l2_subdev *sd, ...@@ -1040,15 +1041,15 @@ static int mipi_csis_get_fmt(struct v4l2_subdev *sd,
struct v4l2_subdev_state *sd_state, struct v4l2_subdev_state *sd_state,
struct v4l2_subdev_format *sdformat) struct v4l2_subdev_format *sdformat)
{ {
struct csi_state *state = mipi_sd_to_csis_state(sd); struct mipi_csis_device *csis = sd_to_mipi_csis_device(sd);
struct v4l2_mbus_framefmt *fmt; struct v4l2_mbus_framefmt *fmt;
fmt = mipi_csis_get_format(state, sd_state, sdformat->which, fmt = mipi_csis_get_format(csis, sd_state, sdformat->which,
sdformat->pad); sdformat->pad);
mutex_lock(&state->lock); mutex_lock(&csis->lock);
sdformat->format = *fmt; sdformat->format = *fmt;
mutex_unlock(&state->lock); mutex_unlock(&csis->lock);
return 0; return 0;
} }
...@@ -1057,7 +1058,7 @@ static int mipi_csis_enum_mbus_code(struct v4l2_subdev *sd, ...@@ -1057,7 +1058,7 @@ static int mipi_csis_enum_mbus_code(struct v4l2_subdev *sd,
struct v4l2_subdev_state *sd_state, struct v4l2_subdev_state *sd_state,
struct v4l2_subdev_mbus_code_enum *code) struct v4l2_subdev_mbus_code_enum *code)
{ {
struct csi_state *state = mipi_sd_to_csis_state(sd); struct mipi_csis_device *csis = sd_to_mipi_csis_device(sd);
/* /*
* The CSIS can't transcode in any way, the source format is identical * The CSIS can't transcode in any way, the source format is identical
...@@ -1069,7 +1070,7 @@ static int mipi_csis_enum_mbus_code(struct v4l2_subdev *sd, ...@@ -1069,7 +1070,7 @@ static int mipi_csis_enum_mbus_code(struct v4l2_subdev *sd,
if (code->index > 0) if (code->index > 0)
return -EINVAL; return -EINVAL;
fmt = mipi_csis_get_format(state, sd_state, code->which, fmt = mipi_csis_get_format(csis, sd_state, code->which,
code->pad); code->pad);
code->code = fmt->code; code->code = fmt->code;
return 0; return 0;
...@@ -1090,7 +1091,7 @@ static int mipi_csis_set_fmt(struct v4l2_subdev *sd, ...@@ -1090,7 +1091,7 @@ static int mipi_csis_set_fmt(struct v4l2_subdev *sd,
struct v4l2_subdev_state *sd_state, struct v4l2_subdev_state *sd_state,
struct v4l2_subdev_format *sdformat) struct v4l2_subdev_format *sdformat)
{ {
struct csi_state *state = mipi_sd_to_csis_state(sd); struct mipi_csis_device *csis = sd_to_mipi_csis_device(sd);
struct csis_pix_format const *csis_fmt; struct csis_pix_format const *csis_fmt;
struct v4l2_mbus_framefmt *fmt; struct v4l2_mbus_framefmt *fmt;
unsigned int align; unsigned int align;
...@@ -1138,10 +1139,10 @@ static int mipi_csis_set_fmt(struct v4l2_subdev *sd, ...@@ -1138,10 +1139,10 @@ static int mipi_csis_set_fmt(struct v4l2_subdev *sd,
&sdformat->format.height, 1, &sdformat->format.height, 1,
CSIS_MAX_PIX_HEIGHT, 0, 0); CSIS_MAX_PIX_HEIGHT, 0, 0);
fmt = mipi_csis_get_format(state, sd_state, sdformat->which, fmt = mipi_csis_get_format(csis, sd_state, sdformat->which,
sdformat->pad); sdformat->pad);
mutex_lock(&state->lock); mutex_lock(&csis->lock);
fmt->code = csis_fmt->code; fmt->code = csis_fmt->code;
fmt->width = sdformat->format.width; fmt->width = sdformat->format.width;
...@@ -1154,7 +1155,7 @@ static int mipi_csis_set_fmt(struct v4l2_subdev *sd, ...@@ -1154,7 +1155,7 @@ static int mipi_csis_set_fmt(struct v4l2_subdev *sd,
sdformat->format = *fmt; sdformat->format = *fmt;
/* Propagate the format from sink to source. */ /* Propagate the format from sink to source. */
fmt = mipi_csis_get_format(state, sd_state, sdformat->which, fmt = mipi_csis_get_format(csis, sd_state, sdformat->which,
CSIS_PAD_SOURCE); CSIS_PAD_SOURCE);
*fmt = sdformat->format; *fmt = sdformat->format;
...@@ -1163,22 +1164,22 @@ static int mipi_csis_set_fmt(struct v4l2_subdev *sd, ...@@ -1163,22 +1164,22 @@ static int mipi_csis_set_fmt(struct v4l2_subdev *sd,
/* Store the CSIS format descriptor for active formats. */ /* Store the CSIS format descriptor for active formats. */
if (sdformat->which == V4L2_SUBDEV_FORMAT_ACTIVE) if (sdformat->which == V4L2_SUBDEV_FORMAT_ACTIVE)
state->csis_fmt = csis_fmt; csis->csis_fmt = csis_fmt;
mutex_unlock(&state->lock); mutex_unlock(&csis->lock);
return 0; return 0;
} }
static int mipi_csis_log_status(struct v4l2_subdev *sd) static int mipi_csis_log_status(struct v4l2_subdev *sd)
{ {
struct csi_state *state = mipi_sd_to_csis_state(sd); struct mipi_csis_device *csis = sd_to_mipi_csis_device(sd);
mutex_lock(&state->lock); mutex_lock(&csis->lock);
mipi_csis_log_counters(state, true); mipi_csis_log_counters(csis, true);
if (state->debug.enable && (state->state & ST_POWERED)) if (csis->debug.enable && (csis->state & ST_POWERED))
mipi_csis_dump_regs(state); mipi_csis_dump_regs(csis);
mutex_unlock(&state->lock); mutex_unlock(&csis->lock);
return 0; return 0;
} }
...@@ -1213,10 +1214,10 @@ static int mipi_csis_link_setup(struct media_entity *entity, ...@@ -1213,10 +1214,10 @@ static int mipi_csis_link_setup(struct media_entity *entity,
const struct media_pad *remote_pad, u32 flags) const struct media_pad *remote_pad, u32 flags)
{ {
struct v4l2_subdev *sd = media_entity_to_v4l2_subdev(entity); struct v4l2_subdev *sd = media_entity_to_v4l2_subdev(entity);
struct csi_state *state = mipi_sd_to_csis_state(sd); struct mipi_csis_device *csis = sd_to_mipi_csis_device(sd);
struct v4l2_subdev *remote_sd; struct v4l2_subdev *remote_sd;
dev_dbg(state->dev, "link setup %s -> %s", remote_pad->entity->name, dev_dbg(csis->dev, "link setup %s -> %s", remote_pad->entity->name,
local_pad->entity->name); local_pad->entity->name);
/* We only care about the link to the source. */ /* We only care about the link to the source. */
...@@ -1226,12 +1227,12 @@ static int mipi_csis_link_setup(struct media_entity *entity, ...@@ -1226,12 +1227,12 @@ static int mipi_csis_link_setup(struct media_entity *entity,
remote_sd = media_entity_to_v4l2_subdev(remote_pad->entity); remote_sd = media_entity_to_v4l2_subdev(remote_pad->entity);
if (flags & MEDIA_LNK_FL_ENABLED) { if (flags & MEDIA_LNK_FL_ENABLED) {
if (state->src_sd) if (csis->src_sd)
return -EBUSY; return -EBUSY;
state->src_sd = remote_sd; csis->src_sd = remote_sd;
} else { } else {
state->src_sd = NULL; csis->src_sd = NULL;
} }
return 0; return 0;
...@@ -1247,18 +1248,18 @@ static const struct media_entity_operations mipi_csis_entity_ops = { ...@@ -1247,18 +1248,18 @@ static const struct media_entity_operations mipi_csis_entity_ops = {
* Async subdev notifier * Async subdev notifier
*/ */
static struct csi_state * static struct mipi_csis_device *
mipi_notifier_to_csis_state(struct v4l2_async_notifier *n) mipi_notifier_to_csis_state(struct v4l2_async_notifier *n)
{ {
return container_of(n, struct csi_state, notifier); return container_of(n, struct mipi_csis_device, notifier);
} }
static int mipi_csis_notify_bound(struct v4l2_async_notifier *notifier, static int mipi_csis_notify_bound(struct v4l2_async_notifier *notifier,
struct v4l2_subdev *sd, struct v4l2_subdev *sd,
struct v4l2_async_subdev *asd) struct v4l2_async_subdev *asd)
{ {
struct csi_state *state = mipi_notifier_to_csis_state(notifier); struct mipi_csis_device *csis = mipi_notifier_to_csis_state(notifier);
struct media_pad *sink = &state->sd.entity.pads[CSIS_PAD_SINK]; struct media_pad *sink = &csis->sd.entity.pads[CSIS_PAD_SINK];
return v4l2_create_fwnode_links_to_pad(sd, sink, 0); return v4l2_create_fwnode_links_to_pad(sd, sink, 0);
} }
...@@ -1267,7 +1268,7 @@ static const struct v4l2_async_notifier_operations mipi_csis_notify_ops = { ...@@ -1267,7 +1268,7 @@ static const struct v4l2_async_notifier_operations mipi_csis_notify_ops = {
.bound = mipi_csis_notify_bound, .bound = mipi_csis_notify_bound,
}; };
static int mipi_csis_async_register(struct csi_state *state) static int mipi_csis_async_register(struct mipi_csis_device *csis)
{ {
struct v4l2_fwnode_endpoint vep = { struct v4l2_fwnode_endpoint vep = {
.bus_type = V4L2_MBUS_CSI2_DPHY, .bus_type = V4L2_MBUS_CSI2_DPHY,
...@@ -1277,9 +1278,9 @@ static int mipi_csis_async_register(struct csi_state *state) ...@@ -1277,9 +1278,9 @@ static int mipi_csis_async_register(struct csi_state *state)
unsigned int i; unsigned int i;
int ret; int ret;
v4l2_async_nf_init(&state->notifier); v4l2_async_nf_init(&csis->notifier);
ep = fwnode_graph_get_endpoint_by_id(dev_fwnode(state->dev), 0, 0, ep = fwnode_graph_get_endpoint_by_id(dev_fwnode(csis->dev), 0, 0,
FWNODE_GRAPH_ENDPOINT_NEXT); FWNODE_GRAPH_ENDPOINT_NEXT);
if (!ep) if (!ep)
return -ENOTCONN; return -ENOTCONN;
...@@ -1290,19 +1291,19 @@ static int mipi_csis_async_register(struct csi_state *state) ...@@ -1290,19 +1291,19 @@ static int mipi_csis_async_register(struct csi_state *state)
for (i = 0; i < vep.bus.mipi_csi2.num_data_lanes; ++i) { for (i = 0; i < vep.bus.mipi_csi2.num_data_lanes; ++i) {
if (vep.bus.mipi_csi2.data_lanes[i] != i + 1) { if (vep.bus.mipi_csi2.data_lanes[i] != i + 1) {
dev_err(state->dev, dev_err(csis->dev,
"data lanes reordering is not supported"); "data lanes reordering is not supported");
ret = -EINVAL; ret = -EINVAL;
goto err_parse; goto err_parse;
} }
} }
state->bus = vep.bus.mipi_csi2; csis->bus = vep.bus.mipi_csi2;
dev_dbg(state->dev, "data lanes: %d\n", state->bus.num_data_lanes); dev_dbg(csis->dev, "data lanes: %d\n", csis->bus.num_data_lanes);
dev_dbg(state->dev, "flags: 0x%08x\n", state->bus.flags); dev_dbg(csis->dev, "flags: 0x%08x\n", csis->bus.flags);
asd = v4l2_async_nf_add_fwnode_remote(&state->notifier, ep, asd = v4l2_async_nf_add_fwnode_remote(&csis->notifier, ep,
struct v4l2_async_subdev); struct v4l2_async_subdev);
if (IS_ERR(asd)) { if (IS_ERR(asd)) {
ret = PTR_ERR(asd); ret = PTR_ERR(asd);
...@@ -1311,13 +1312,13 @@ static int mipi_csis_async_register(struct csi_state *state) ...@@ -1311,13 +1312,13 @@ static int mipi_csis_async_register(struct csi_state *state)
fwnode_handle_put(ep); fwnode_handle_put(ep);
state->notifier.ops = &mipi_csis_notify_ops; csis->notifier.ops = &mipi_csis_notify_ops;
ret = v4l2_async_subdev_nf_register(&state->sd, &state->notifier); ret = v4l2_async_subdev_nf_register(&csis->sd, &csis->notifier);
if (ret) if (ret)
return ret; return ret;
return v4l2_async_register_subdev(&state->sd); return v4l2_async_register_subdev(&csis->sd);
err_parse: err_parse:
fwnode_handle_put(ep); fwnode_handle_put(ep);
...@@ -1332,23 +1333,23 @@ static int mipi_csis_async_register(struct csi_state *state) ...@@ -1332,23 +1333,23 @@ static int mipi_csis_async_register(struct csi_state *state)
static int mipi_csis_pm_suspend(struct device *dev, bool runtime) static int mipi_csis_pm_suspend(struct device *dev, bool runtime)
{ {
struct v4l2_subdev *sd = dev_get_drvdata(dev); struct v4l2_subdev *sd = dev_get_drvdata(dev);
struct csi_state *state = mipi_sd_to_csis_state(sd); struct mipi_csis_device *csis = sd_to_mipi_csis_device(sd);
int ret = 0; int ret = 0;
mutex_lock(&state->lock); mutex_lock(&csis->lock);
if (state->state & ST_POWERED) { if (csis->state & ST_POWERED) {
mipi_csis_stop_stream(state); mipi_csis_stop_stream(csis);
ret = mipi_csis_phy_disable(state); ret = mipi_csis_phy_disable(csis);
if (ret) if (ret)
goto unlock; goto unlock;
mipi_csis_clk_disable(state); mipi_csis_clk_disable(csis);
state->state &= ~ST_POWERED; csis->state &= ~ST_POWERED;
if (!runtime) if (!runtime)
state->state |= ST_SUSPENDED; csis->state |= ST_SUSPENDED;
} }
unlock: unlock:
mutex_unlock(&state->lock); mutex_unlock(&csis->lock);
return ret ? -EAGAIN : 0; return ret ? -EAGAIN : 0;
} }
...@@ -1356,28 +1357,28 @@ static int mipi_csis_pm_suspend(struct device *dev, bool runtime) ...@@ -1356,28 +1357,28 @@ static int mipi_csis_pm_suspend(struct device *dev, bool runtime)
static int mipi_csis_pm_resume(struct device *dev, bool runtime) static int mipi_csis_pm_resume(struct device *dev, bool runtime)
{ {
struct v4l2_subdev *sd = dev_get_drvdata(dev); struct v4l2_subdev *sd = dev_get_drvdata(dev);
struct csi_state *state = mipi_sd_to_csis_state(sd); struct mipi_csis_device *csis = sd_to_mipi_csis_device(sd);
int ret = 0; int ret = 0;
mutex_lock(&state->lock); mutex_lock(&csis->lock);
if (!runtime && !(state->state & ST_SUSPENDED)) if (!runtime && !(csis->state & ST_SUSPENDED))
goto unlock; goto unlock;
if (!(state->state & ST_POWERED)) { if (!(csis->state & ST_POWERED)) {
ret = mipi_csis_phy_enable(state); ret = mipi_csis_phy_enable(csis);
if (ret) if (ret)
goto unlock; goto unlock;
state->state |= ST_POWERED; csis->state |= ST_POWERED;
mipi_csis_clk_enable(state); mipi_csis_clk_enable(csis);
} }
if (state->state & ST_STREAMING) if (csis->state & ST_STREAMING)
mipi_csis_start_stream(state); mipi_csis_start_stream(csis);
state->state &= ~ST_SUSPENDED; csis->state &= ~ST_SUSPENDED;
unlock: unlock:
mutex_unlock(&state->lock); mutex_unlock(&csis->lock);
return ret ? -EAGAIN : 0; return ret ? -EAGAIN : 0;
} }
...@@ -1412,14 +1413,14 @@ static const struct dev_pm_ops mipi_csis_pm_ops = { ...@@ -1412,14 +1413,14 @@ static const struct dev_pm_ops mipi_csis_pm_ops = {
* Probe/remove & platform driver * Probe/remove & platform driver
*/ */
static int mipi_csis_subdev_init(struct csi_state *state) static int mipi_csis_subdev_init(struct mipi_csis_device *csis)
{ {
struct v4l2_subdev *sd = &state->sd; struct v4l2_subdev *sd = &csis->sd;
v4l2_subdev_init(sd, &mipi_csis_subdev_ops); v4l2_subdev_init(sd, &mipi_csis_subdev_ops);
sd->owner = THIS_MODULE; sd->owner = THIS_MODULE;
snprintf(sd->name, sizeof(sd->name), "csis-%s", snprintf(sd->name, sizeof(sd->name), "csis-%s",
dev_name(state->dev)); dev_name(csis->dev));
sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE; sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE;
sd->ctrl_handler = NULL; sd->ctrl_handler = NULL;
...@@ -1427,26 +1428,26 @@ static int mipi_csis_subdev_init(struct csi_state *state) ...@@ -1427,26 +1428,26 @@ static int mipi_csis_subdev_init(struct csi_state *state)
sd->entity.function = MEDIA_ENT_F_VID_IF_BRIDGE; sd->entity.function = MEDIA_ENT_F_VID_IF_BRIDGE;
sd->entity.ops = &mipi_csis_entity_ops; sd->entity.ops = &mipi_csis_entity_ops;
sd->dev = state->dev; sd->dev = csis->dev;
state->csis_fmt = &mipi_csis_formats[0]; csis->csis_fmt = &mipi_csis_formats[0];
mipi_csis_init_cfg(sd, NULL); mipi_csis_init_cfg(sd, NULL);
state->pads[CSIS_PAD_SINK].flags = MEDIA_PAD_FL_SINK csis->pads[CSIS_PAD_SINK].flags = MEDIA_PAD_FL_SINK
| MEDIA_PAD_FL_MUST_CONNECT; | MEDIA_PAD_FL_MUST_CONNECT;
state->pads[CSIS_PAD_SOURCE].flags = MEDIA_PAD_FL_SOURCE csis->pads[CSIS_PAD_SOURCE].flags = MEDIA_PAD_FL_SOURCE
| MEDIA_PAD_FL_MUST_CONNECT; | MEDIA_PAD_FL_MUST_CONNECT;
return media_entity_pads_init(&sd->entity, CSIS_PADS_NUM, return media_entity_pads_init(&sd->entity, CSIS_PADS_NUM,
state->pads); csis->pads);
} }
static int mipi_csis_parse_dt(struct csi_state *state) static int mipi_csis_parse_dt(struct mipi_csis_device *csis)
{ {
struct device_node *node = state->dev->of_node; struct device_node *node = csis->dev->of_node;
if (of_property_read_u32(node, "clock-frequency", if (of_property_read_u32(node, "clock-frequency",
&state->clk_frequency)) &csis->clk_frequency))
state->clk_frequency = DEFAULT_SCLK_CSIS_FREQ; csis->clk_frequency = DEFAULT_SCLK_CSIS_FREQ;
return 0; return 0;
} }
...@@ -1454,78 +1455,78 @@ static int mipi_csis_parse_dt(struct csi_state *state) ...@@ -1454,78 +1455,78 @@ static int mipi_csis_parse_dt(struct csi_state *state)
static int mipi_csis_probe(struct platform_device *pdev) static int mipi_csis_probe(struct platform_device *pdev)
{ {
struct device *dev = &pdev->dev; struct device *dev = &pdev->dev;
struct csi_state *state; struct mipi_csis_device *csis;
int irq; int irq;
int ret; int ret;
state = devm_kzalloc(dev, sizeof(*state), GFP_KERNEL); csis = devm_kzalloc(dev, sizeof(*csis), GFP_KERNEL);
if (!state) if (!csis)
return -ENOMEM; return -ENOMEM;
mutex_init(&state->lock); mutex_init(&csis->lock);
spin_lock_init(&state->slock); spin_lock_init(&csis->slock);
state->dev = dev; csis->dev = dev;
state->info = of_device_get_match_data(dev); csis->info = of_device_get_match_data(dev);
memcpy(state->events, mipi_csis_events, sizeof(state->events)); memcpy(csis->events, mipi_csis_events, sizeof(csis->events));
/* Parse DT properties. */ /* Parse DT properties. */
ret = mipi_csis_parse_dt(state); ret = mipi_csis_parse_dt(csis);
if (ret < 0) { if (ret < 0) {
dev_err(dev, "Failed to parse device tree: %d\n", ret); dev_err(dev, "Failed to parse device tree: %d\n", ret);
return ret; return ret;
} }
/* Acquire resources. */ /* Acquire resources. */
state->regs = devm_platform_ioremap_resource(pdev, 0); csis->regs = devm_platform_ioremap_resource(pdev, 0);
if (IS_ERR(state->regs)) if (IS_ERR(csis->regs))
return PTR_ERR(state->regs); return PTR_ERR(csis->regs);
irq = platform_get_irq(pdev, 0); irq = platform_get_irq(pdev, 0);
if (irq < 0) if (irq < 0)
return irq; return irq;
ret = mipi_csis_phy_init(state); ret = mipi_csis_phy_init(csis);
if (ret < 0) if (ret < 0)
return ret; return ret;
ret = mipi_csis_clk_get(state); ret = mipi_csis_clk_get(csis);
if (ret < 0) if (ret < 0)
return ret; return ret;
/* Reset PHY and enable the clocks. */ /* Reset PHY and enable the clocks. */
mipi_csis_phy_reset(state); mipi_csis_phy_reset(csis);
ret = mipi_csis_clk_enable(state); ret = mipi_csis_clk_enable(csis);
if (ret < 0) { if (ret < 0) {
dev_err(state->dev, "failed to enable clocks: %d\n", ret); dev_err(csis->dev, "failed to enable clocks: %d\n", ret);
return ret; return ret;
} }
/* Now that the hardware is initialized, request the interrupt. */ /* Now that the hardware is initialized, request the interrupt. */
ret = devm_request_irq(dev, irq, mipi_csis_irq_handler, 0, ret = devm_request_irq(dev, irq, mipi_csis_irq_handler, 0,
dev_name(dev), state); dev_name(dev), csis);
if (ret) { if (ret) {
dev_err(dev, "Interrupt request failed\n"); dev_err(dev, "Interrupt request failed\n");
goto disable_clock; goto disable_clock;
} }
/* Initialize and register the subdev. */ /* Initialize and register the subdev. */
ret = mipi_csis_subdev_init(state); ret = mipi_csis_subdev_init(csis);
if (ret < 0) if (ret < 0)
goto disable_clock; goto disable_clock;
platform_set_drvdata(pdev, &state->sd); platform_set_drvdata(pdev, &csis->sd);
ret = mipi_csis_async_register(state); ret = mipi_csis_async_register(csis);
if (ret < 0) { if (ret < 0) {
dev_err(dev, "async register failed: %d\n", ret); dev_err(dev, "async register failed: %d\n", ret);
goto cleanup; goto cleanup;
} }
/* Initialize debugfs. */ /* Initialize debugfs. */
mipi_csis_debugfs_init(state); mipi_csis_debugfs_init(csis);
/* Enable runtime PM. */ /* Enable runtime PM. */
pm_runtime_enable(dev); pm_runtime_enable(dev);
...@@ -1536,20 +1537,20 @@ static int mipi_csis_probe(struct platform_device *pdev) ...@@ -1536,20 +1537,20 @@ static int mipi_csis_probe(struct platform_device *pdev)
} }
dev_info(dev, "lanes: %d, freq: %u\n", dev_info(dev, "lanes: %d, freq: %u\n",
state->bus.num_data_lanes, state->clk_frequency); csis->bus.num_data_lanes, csis->clk_frequency);
return 0; return 0;
unregister_all: unregister_all:
mipi_csis_debugfs_exit(state); mipi_csis_debugfs_exit(csis);
cleanup: cleanup:
media_entity_cleanup(&state->sd.entity); media_entity_cleanup(&csis->sd.entity);
v4l2_async_nf_unregister(&state->notifier); v4l2_async_nf_unregister(&csis->notifier);
v4l2_async_nf_cleanup(&state->notifier); v4l2_async_nf_cleanup(&csis->notifier);
v4l2_async_unregister_subdev(&state->sd); v4l2_async_unregister_subdev(&csis->sd);
disable_clock: disable_clock:
mipi_csis_clk_disable(state); mipi_csis_clk_disable(csis);
mutex_destroy(&state->lock); mutex_destroy(&csis->lock);
return ret; return ret;
} }
...@@ -1557,18 +1558,18 @@ static int mipi_csis_probe(struct platform_device *pdev) ...@@ -1557,18 +1558,18 @@ static int mipi_csis_probe(struct platform_device *pdev)
static int mipi_csis_remove(struct platform_device *pdev) static int mipi_csis_remove(struct platform_device *pdev)
{ {
struct v4l2_subdev *sd = platform_get_drvdata(pdev); struct v4l2_subdev *sd = platform_get_drvdata(pdev);
struct csi_state *state = mipi_sd_to_csis_state(sd); struct mipi_csis_device *csis = sd_to_mipi_csis_device(sd);
mipi_csis_debugfs_exit(state); mipi_csis_debugfs_exit(csis);
v4l2_async_nf_unregister(&state->notifier); v4l2_async_nf_unregister(&csis->notifier);
v4l2_async_nf_cleanup(&state->notifier); v4l2_async_nf_cleanup(&csis->notifier);
v4l2_async_unregister_subdev(&state->sd); v4l2_async_unregister_subdev(&csis->sd);
pm_runtime_disable(&pdev->dev); pm_runtime_disable(&pdev->dev);
mipi_csis_pm_suspend(&pdev->dev, true); mipi_csis_pm_suspend(&pdev->dev, true);
mipi_csis_clk_disable(state); mipi_csis_clk_disable(csis);
media_entity_cleanup(&state->sd.entity); media_entity_cleanup(&csis->sd.entity);
mutex_destroy(&state->lock); mutex_destroy(&csis->lock);
pm_runtime_set_suspended(&pdev->dev); pm_runtime_set_suspended(&pdev->dev);
return 0; return 0;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment