2 * Tegra CSI2 device common APIs
4 * Copyright (c) 2016-2017, NVIDIA CORPORATION. All rights reserved.
6 * Author: Bryan Wu <pengw@nvidia.com>
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 as
10 * published by the Free Software Foundation.
13 #include <linux/device.h>
14 #include <linux/clk/tegra.h>
15 #include "camera/csi/csi.h"
16 #include "camera/vi/mc_common.h"
17 #include "mipical/mipi_cal.h"
18 #include "nvhost_acm.h"
19 #include <linux/clk/tegra.h>
21 static void csi_write(struct tegra_csi_channel *chan, unsigned int addr,
24 struct tegra_csi_device *csi = chan->csi;
26 writel(val, (csi->iomem[port] + addr));
29 static u32 csi_read(struct tegra_csi_channel *chan, unsigned int addr,
32 struct tegra_csi_device *csi = chan->csi;
34 return readl((csi->iomem[port] + addr));
37 /* Pixel parser registers accessors */
38 static void pp_write(struct tegra_csi_port *port, u32 addr, u32 val)
40 writel(val, port->pixel_parser + addr);
43 static u32 pp_read(struct tegra_csi_port *port, u32 addr)
45 return readl(port->pixel_parser + addr);
48 /* CSI CIL registers accessors */
49 static void cil_write(struct tegra_csi_port *port, u32 addr, u32 val)
51 writel(val, port->cil + addr);
54 static u32 cil_read(struct tegra_csi_port *port, u32 addr)
56 return readl(port->cil + addr);
59 /* Test pattern generator registers accessor */
60 static void tpg_write(struct tegra_csi_port *port,
61 unsigned int addr, u32 val)
63 writel(val, port->tpg + addr);
66 int tegra_csi_error(struct tegra_csi_channel *chan,
67 enum tegra_csi_port_num port_num)
69 struct tegra_csi_port *port;
73 port = &chan->ports[port_num];
75 * only uncorrectable header error and multi-bit
76 * transmission errors are checked as they cannot be
77 * corrected automatically
79 val = pp_read(port, TEGRA_CSI_PIXEL_PARSER_STATUS);
81 pp_write(port, TEGRA_CSI_PIXEL_PARSER_STATUS, val);
83 val = cil_read(port, TEGRA_CSI_CIL_STATUS);
85 cil_write(port, TEGRA_CSI_CIL_STATUS, val);
87 val = cil_read(port, TEGRA_CSI_CILX_STATUS);
88 err |= val & 0x00020020;
89 cil_write(port, TEGRA_CSI_CILX_STATUS, val);
94 void tegra_csi_status(struct tegra_csi_channel *chan,
95 enum tegra_csi_port_num port_num)
99 struct tegra_csi_port *port;
101 for (i = 0; i < chan->numports; i++) {
102 port = &chan->ports[i];
103 val = pp_read(port, TEGRA_CSI_PIXEL_PARSER_STATUS);
105 dev_dbg(chan->csi->dev,
106 "TEGRA_CSI_PIXEL_PARSER_STATUS 0x%08x\n",
109 val = cil_read(port, TEGRA_CSI_CIL_STATUS);
110 dev_dbg(chan->csi->dev,
111 "TEGRA_CSI_CIL_STATUS 0x%08x\n", val);
113 val = cil_read(port, TEGRA_CSI_CILX_STATUS);
114 dev_dbg(chan->csi->dev,
115 "TEGRA_CSI_CILX_STATUS 0x%08x\n", val);
118 EXPORT_SYMBOL(tegra_csi_status);
120 void tegra_csi_error_recover(struct tegra_csi_channel *chan,
121 enum tegra_csi_port_num port_num)
123 struct tegra_csi_port *port;
124 struct tegra_csi_device *csi;
129 for (i = 0; i < chan->numports; i++) {
130 port = &chan->ports[i];
132 if (port->lanes == 4) {
133 int port_val = ((port_num >> 1) << 1);
134 struct tegra_csi_port *port_a =
135 &chan->ports[port_val];
136 struct tegra_csi_port *port_b =
137 &chan->ports[port_val+1];
140 TEGRA_CSI_PATTERN_GENERATOR_CTRL, PG_ENABLE);
142 TEGRA_CSI_PATTERN_GENERATOR_CTRL, PG_ENABLE);
144 TEGRA_CSI_CIL_SW_SENSOR_RESET, 0x1);
146 TEGRA_CSI_CIL_SW_SENSOR_RESET, 0x1);
147 csi_write(chan, TEGRA_CSI_CSI_SW_STATUS_RESET, 0x1,
149 /* sleep for clock cycles to drain the Rx FIFO */
150 usleep_range(10, 20);
152 TEGRA_CSI_CIL_SW_SENSOR_RESET, 0x0);
154 TEGRA_CSI_CIL_SW_SENSOR_RESET, 0x0);
156 TEGRA_CSI_CSI_SW_STATUS_RESET,
159 TEGRA_CSI_PATTERN_GENERATOR_CTRL, PG_DISABLE);
161 TEGRA_CSI_PATTERN_GENERATOR_CTRL, PG_DISABLE);
164 TEGRA_CSI_PATTERN_GENERATOR_CTRL, PG_ENABLE);
166 TEGRA_CSI_CIL_SW_SENSOR_RESET, 0x1);
168 TEGRA_CSI_CSI_SW_STATUS_RESET,
170 /* sleep for clock cycles to drain the Rx FIFO */
171 usleep_range(10, 20);
173 TEGRA_CSI_CIL_SW_SENSOR_RESET, 0x0);
175 TEGRA_CSI_CSI_SW_STATUS_RESET,
178 TEGRA_CSI_PATTERN_GENERATOR_CTRL, PG_DISABLE);
184 static int tpg_clk_enable(struct tegra_csi_device *csi)
188 mutex_lock(&csi->source_update);
189 if (csi->tpg_active != 1) {
190 mutex_unlock(&csi->source_update);
193 mutex_unlock(&csi->source_update);
195 clk_set_rate(csi->plld, TEGRA_CLOCK_TPG);
196 err = clk_prepare_enable(csi->plld);
198 dev_err(csi->dev, "pll_d enable failed");
202 err = clk_prepare_enable(csi->plld_dsi);
204 dev_err(csi->dev, "pll_d enable failed");
207 tegra210_csi_source_from_plld();
210 clk_disable_unprepare(csi->plld);
214 static int tpg_clk_disable(struct tegra_csi_device *csi)
218 mutex_lock(&csi->source_update);
219 if (csi->tpg_active != 0) {
220 mutex_unlock(&csi->source_update);
223 mutex_unlock(&csi->source_update);
224 tegra210_csi_source_from_brick();
225 clk_disable_unprepare(csi->plld_dsi);
226 clk_disable_unprepare(csi->plld);
231 static int csi2_tpg_start_streaming(struct tegra_csi_channel *chan,
232 enum tegra_csi_port_num port_num)
234 struct tegra_csi_port *port = &chan->ports[port_num];
236 tpg_write(port, TEGRA_CSI_PATTERN_GENERATOR_CTRL,
237 ((chan->pg_mode - 1) << PG_MODE_OFFSET) |
239 tpg_write(port, TEGRA_CSI_PG_BLANK,
240 port->v_blank << PG_VBLANK_OFFSET |
242 tpg_write(port, TEGRA_CSI_PG_PHASE, 0x0);
243 tpg_write(port, TEGRA_CSI_PG_RED_FREQ,
244 (0x10 << PG_RED_VERT_INIT_FREQ_OFFSET) |
245 (0x10 << PG_RED_HOR_INIT_FREQ_OFFSET));
246 tpg_write(port, TEGRA_CSI_PG_RED_FREQ_RATE, 0x0);
247 tpg_write(port, TEGRA_CSI_PG_GREEN_FREQ,
248 (0x10 << PG_GREEN_VERT_INIT_FREQ_OFFSET) |
249 (0x10 << PG_GREEN_HOR_INIT_FREQ_OFFSET));
250 tpg_write(port, TEGRA_CSI_PG_GREEN_FREQ_RATE, 0x0);
251 tpg_write(port, TEGRA_CSI_PG_BLUE_FREQ,
252 (0x10 << PG_BLUE_VERT_INIT_FREQ_OFFSET) |
253 (0x10 << PG_BLUE_HOR_INIT_FREQ_OFFSET));
254 tpg_write(port, TEGRA_CSI_PG_BLUE_FREQ_RATE, 0x0);
258 int csi2_start_streaming(struct tegra_csi_channel *chan,
259 enum tegra_csi_port_num port_num)
261 struct tegra_csi_port *port = &chan->ports[port_num];
262 int csi_port, csi_lanes;
264 csi_port = chan->ports[port_num].num;
265 csi_lanes = chan->ports[port_num].lanes;
267 csi_write(chan, TEGRA_CSI_CLKEN_OVERRIDE, 0, csi_port >> 1);
269 /* Clean up status */
270 pp_write(port, TEGRA_CSI_PIXEL_PARSER_STATUS, 0xFFFFFFFF);
271 cil_write(port, TEGRA_CSI_CIL_STATUS, 0xFFFFFFFF);
272 cil_write(port, TEGRA_CSI_CILX_STATUS, 0xFFFFFFFF);
274 cil_write(port, TEGRA_CSI_CIL_INTERRUPT_MASK, 0x0);
276 /* CIL PHY registers setup */
277 cil_write(port, TEGRA_CSI_CIL_PAD_CONFIG0, 0x0);
278 cil_write(port, TEGRA_CSI_CIL_PHY_CONTROL,
279 BYPASS_LP_SEQ | 0xA);
282 * The CSI unit provides for connection of up to six cameras in
283 * the system and is organized as three identical instances of
284 * two MIPI support blocks, each with a separate 4-lane
285 * interface that can be configured as a single camera with 4
286 * lanes or as a dual camera with 2 lanes available for each
289 if (csi_lanes == 4) {
290 unsigned int cilb_offset;
292 cilb_offset = TEGRA_CSI_CIL_OFFSET + TEGRA_CSI_PORT_OFFSET;
294 cil_write(port, TEGRA_CSI_CIL_PAD_CONFIG0,
296 csi_write(chan, cilb_offset + TEGRA_CSI_CIL_PAD_CONFIG0, 0x0,
298 csi_write(chan, cilb_offset + TEGRA_CSI_CIL_INTERRUPT_MASK, 0x0,
300 cil_write(port, TEGRA_CSI_CIL_PHY_CONTROL,
301 BYPASS_LP_SEQ | 0xA);
302 csi_write(chan, cilb_offset + TEGRA_CSI_CIL_PHY_CONTROL,
303 BYPASS_LP_SEQ | 0xA, csi_port >> 1);
304 csi_write(chan, TEGRA_CSI_PHY_CIL_COMMAND,
305 CSI_A_PHY_CIL_ENABLE | CSI_B_PHY_CIL_ENABLE,
308 u32 val = csi_read(chan, TEGRA_CSI_PHY_CIL_COMMAND,
312 TEGRA_CSI_CIL_OFFSET + TEGRA_CSI_CIL_PAD_CONFIG0, 0x0,
314 val |= ((csi_port & 0x1) == PORT_A) ? CSI_A_PHY_CIL_ENABLE :
315 CSI_B_PHY_CIL_ENABLE;
316 csi_write(chan, TEGRA_CSI_PHY_CIL_COMMAND, val,
319 /* CSI pixel parser registers setup */
320 pp_write(port, TEGRA_CSI_PIXEL_STREAM_PP_COMMAND,
321 (0xF << CSI_PP_START_MARKER_FRAME_MAX_OFFSET) |
322 CSI_PP_SINGLE_SHOT_ENABLE | CSI_PP_RST);
323 pp_write(port, TEGRA_CSI_PIXEL_PARSER_INTERRUPT_MASK, 0x0);
324 pp_write(port, TEGRA_CSI_PIXEL_STREAM_CONTROL0,
325 CSI_PP_PACKET_HEADER_SENT |
326 CSI_PP_DATA_IDENTIFIER_ENABLE |
327 CSI_PP_WORD_COUNT_SELECT_HEADER |
328 CSI_PP_CRC_CHECK_ENABLE | CSI_PP_WC_CHECK |
329 CSI_PP_OUTPUT_FORMAT_STORE | CSI_PPA_PAD_LINE_NOPAD |
330 CSI_PP_HEADER_EC_DISABLE | CSI_PPA_PAD_FRAME_NOPAD |
332 pp_write(port, TEGRA_CSI_PIXEL_STREAM_CONTROL1,
333 (0x1 << CSI_PP_TOP_FIELD_FRAME_OFFSET) |
334 (0x1 << CSI_PP_TOP_FIELD_FRAME_MASK_OFFSET));
335 pp_write(port, TEGRA_CSI_PIXEL_STREAM_GAP,
336 0x14 << PP_FRAME_MIN_GAP_OFFSET);
337 pp_write(port, TEGRA_CSI_PIXEL_STREAM_EXPECTED_FRAME, 0x0);
338 pp_write(port, TEGRA_CSI_INPUT_STREAM_CONTROL,
339 (0x3f << CSI_SKIP_PACKET_THRESHOLD_OFFSET) |
343 tpg_clk_enable(chan->csi);
344 csi2_tpg_start_streaming(chan, port_num);
347 pp_write(port, TEGRA_CSI_PIXEL_STREAM_PP_COMMAND,
348 (0xF << CSI_PP_START_MARKER_FRAME_MAX_OFFSET) |
349 CSI_PP_SINGLE_SHOT_ENABLE | CSI_PP_ENABLE);
353 void csi2_stop_streaming(struct tegra_csi_channel *chan,
354 enum tegra_csi_port_num port_num)
356 struct tegra_csi_port *port = &chan->ports[port_num];
360 tpg_write(port, TEGRA_CSI_PATTERN_GENERATOR_CTRL, PG_DISABLE);
361 tpg_clk_disable(chan->csi);
364 pr_err("%s:no port\n", __func__);
367 pp_write(port, TEGRA_CSI_PIXEL_STREAM_PP_COMMAND,
368 (0xF << CSI_PP_START_MARKER_FRAME_MAX_OFFSET) |
372 int csi2_hw_init(struct tegra_csi_device *csi)
375 struct tegra_csi_channel *it;
376 struct tegra_csi_port *port;
378 csi->iomem[0] = (csi->iomem_base + TEGRA_CSI_PIXEL_PARSER_0_BASE);
379 csi->iomem[1] = (csi->iomem_base + TEGRA_CSI_PIXEL_PARSER_2_BASE);
380 csi->iomem[2] = (csi->iomem_base + TEGRA_CSI_PIXEL_PARSER_4_BASE);
381 list_for_each_entry(it, &csi->csi_chans, list) {
382 for (i = 0; i < it->numports; i++) {
383 port = &it->ports[i];
384 csi_port = it->ports[i].num;
385 port->pixel_parser = csi->iomem[csi_port >> 1] +
386 (csi_port % 2) * TEGRA_CSI_PORT_OFFSET;
387 port->cil = port->pixel_parser + TEGRA_CSI_CIL_OFFSET;
388 port->tpg = port->pixel_parser + TEGRA_CSI_TPG_OFFSET;
391 csi->plld = devm_clk_get(csi->dev, "pll_d");
392 if (IS_ERR(csi->plld)) {
393 dev_err(csi->dev, "Fail to get pll_d\n");
394 return PTR_ERR(csi->plld);
396 csi->plld_dsi = devm_clk_get(csi->dev, "pll_d_dsi_out");
397 if (IS_ERR(csi->plld_dsi)) {
398 dev_err(csi->dev, "Fail to get pll_d_dsi_out\n");
399 return PTR_ERR(csi->plld_dsi);
404 int csi2_mipi_cal(struct tegra_csi_channel *chan)
406 unsigned int lanes, num_ports, val, csi_port;
407 struct tegra_csi_port *port;
408 struct tegra_csi_device *csi = chan->csi;
413 nvhost_module_enable_clk(csi->dev);
414 while (num_ports < chan->numports) {
415 port = &chan->ports[num_ports];
416 csi_port = port->num;
417 dev_dbg(csi->dev, "Calibrate csi port %d\n", port->num);
419 if (chan->numlanes == 2) {
420 lanes |= CSIA << csi_port;
421 val = csi_read(chan, TEGRA_CSI_PHY_CIL_COMMAND,
424 TEGRA_CSI_CIL_OFFSET +
425 TEGRA_CSI_CIL_PAD_CONFIG0, 0x0, csi_port >> 1);
426 val |= ((csi_port & 0x1) == PORT_A) ?
427 CSI_A_PHY_CIL_ENABLE : CSI_B_PHY_CIL_ENABLE;
428 csi_write(chan, TEGRA_CSI_PHY_CIL_COMMAND, val,
431 lanes |= (CSIA | CSIB) << port->num;
432 csi_write(chan, TEGRA_CSI_PHY_CIL_COMMAND,
433 CSI_A_PHY_CIL_ENABLE | CSI_B_PHY_CIL_ENABLE,
440 "Selected no CSI lane, cannot do calibration");
443 nvhost_module_disable_clk(csi->dev);
444 return tegra_mipi_calibration(lanes);
447 int csi2_power_on(struct tegra_csi_device *csi)
451 int csi2_power_off(struct tegra_csi_device *csi)
455 const struct tegra_csi_fops csi2_fops = {
456 .csi_power_on = csi2_power_on,
457 .csi_power_off = csi2_power_off,
458 .csi_start_streaming = csi2_start_streaming,
459 .csi_stop_streaming = csi2_stop_streaming,
460 .mipical = csi2_mipi_cal,
461 .hw_init = csi2_hw_init,
463 EXPORT_SYMBOL(csi2_fops);