cx25821-video-upstream.c 18 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677
  1. /*
  2. * Driver for the Conexant CX25821 PCIe bridge
  3. *
  4. * Copyright (C) 2009 Conexant Systems Inc.
  5. * Authors <hiep.huynh@conexant.com>, <shu.lin@conexant.com>
  6. *
  7. * This program is free software; you can redistribute it and/or modify
  8. * it under the terms of the GNU General Public License as published by
  9. * the Free Software Foundation; either version 2 of the License, or
  10. * (at your option) any later version.
  11. *
  12. * This program is distributed in the hope that it will be useful,
  13. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  14. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  15. *
  16. * GNU General Public License for more details.
  17. *
  18. * You should have received a copy of the GNU General Public License
  19. * along with this program; if not, write to the Free Software
  20. * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  21. */
  22. #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
  23. #include "cx25821-video.h"
  24. #include "cx25821-video-upstream.h"
  25. #include <linux/errno.h>
  26. #include <linux/kernel.h>
  27. #include <linux/init.h>
  28. #include <linux/module.h>
  29. #include <linux/slab.h>
  30. MODULE_DESCRIPTION("v4l2 driver module for cx25821 based TV cards");
  31. MODULE_AUTHOR("Hiep Huynh <hiep.huynh@conexant.com>");
  32. MODULE_LICENSE("GPL");
  33. static int _intr_msk = FLD_VID_SRC_RISC1 | FLD_VID_SRC_UF | FLD_VID_SRC_SYNC |
  34. FLD_VID_SRC_OPC_ERR;
  35. int cx25821_sram_channel_setup_upstream(struct cx25821_dev *dev,
  36. const struct sram_channel *ch,
  37. unsigned int bpl, u32 risc)
  38. {
  39. unsigned int i, lines;
  40. u32 cdt;
  41. if (ch->cmds_start == 0) {
  42. cx_write(ch->ptr1_reg, 0);
  43. cx_write(ch->ptr2_reg, 0);
  44. cx_write(ch->cnt2_reg, 0);
  45. cx_write(ch->cnt1_reg, 0);
  46. return 0;
  47. }
  48. bpl = (bpl + 7) & ~7; /* alignment */
  49. cdt = ch->cdt;
  50. lines = ch->fifo_size / bpl;
  51. if (lines > 4)
  52. lines = 4;
  53. BUG_ON(lines < 2);
  54. /* write CDT */
  55. for (i = 0; i < lines; i++) {
  56. cx_write(cdt + 16 * i, ch->fifo_start + bpl * i);
  57. cx_write(cdt + 16 * i + 4, 0);
  58. cx_write(cdt + 16 * i + 8, 0);
  59. cx_write(cdt + 16 * i + 12, 0);
  60. }
  61. /* write CMDS */
  62. cx_write(ch->cmds_start + 0, risc);
  63. cx_write(ch->cmds_start + 4, 0);
  64. cx_write(ch->cmds_start + 8, cdt);
  65. cx_write(ch->cmds_start + 12, (lines * 16) >> 3);
  66. cx_write(ch->cmds_start + 16, ch->ctrl_start);
  67. cx_write(ch->cmds_start + 20, VID_IQ_SIZE_DW);
  68. for (i = 24; i < 80; i += 4)
  69. cx_write(ch->cmds_start + i, 0);
  70. /* fill registers */
  71. cx_write(ch->ptr1_reg, ch->fifo_start);
  72. cx_write(ch->ptr2_reg, cdt);
  73. cx_write(ch->cnt2_reg, (lines * 16) >> 3);
  74. cx_write(ch->cnt1_reg, (bpl >> 3) - 1);
  75. return 0;
  76. }
  77. static __le32 *cx25821_update_riscprogram(struct cx25821_channel *chan,
  78. __le32 *rp, unsigned int offset,
  79. unsigned int bpl, u32 sync_line,
  80. unsigned int lines, int fifo_enable,
  81. int field_type)
  82. {
  83. struct cx25821_video_out_data *out = chan->out;
  84. unsigned int line, i;
  85. int dist_betwn_starts = bpl * 2;
  86. *(rp++) = cpu_to_le32(RISC_RESYNC | sync_line);
  87. if (USE_RISC_NOOP_VIDEO) {
  88. for (i = 0; i < NUM_NO_OPS; i++)
  89. *(rp++) = cpu_to_le32(RISC_NOOP);
  90. }
  91. /* scan lines */
  92. for (line = 0; line < lines; line++) {
  93. *(rp++) = cpu_to_le32(RISC_READ | RISC_SOL | RISC_EOL | bpl);
  94. *(rp++) = cpu_to_le32(out->_data_buf_phys_addr + offset);
  95. *(rp++) = cpu_to_le32(0); /* bits 63-32 */
  96. if ((lines <= NTSC_FIELD_HEIGHT)
  97. || (line < (NTSC_FIELD_HEIGHT - 1)) || !(out->is_60hz)) {
  98. offset += dist_betwn_starts;
  99. }
  100. }
  101. return rp;
  102. }
  103. static __le32 *cx25821_risc_field_upstream(struct cx25821_channel *chan, __le32 *rp,
  104. dma_addr_t databuf_phys_addr,
  105. unsigned int offset, u32 sync_line,
  106. unsigned int bpl, unsigned int lines,
  107. int fifo_enable, int field_type)
  108. {
  109. struct cx25821_video_out_data *out = chan->out;
  110. unsigned int line, i;
  111. const struct sram_channel *sram_ch = chan->sram_channels;
  112. int dist_betwn_starts = bpl * 2;
  113. /* sync instruction */
  114. if (sync_line != NO_SYNC_LINE)
  115. *(rp++) = cpu_to_le32(RISC_RESYNC | sync_line);
  116. if (USE_RISC_NOOP_VIDEO) {
  117. for (i = 0; i < NUM_NO_OPS; i++)
  118. *(rp++) = cpu_to_le32(RISC_NOOP);
  119. }
  120. /* scan lines */
  121. for (line = 0; line < lines; line++) {
  122. *(rp++) = cpu_to_le32(RISC_READ | RISC_SOL | RISC_EOL | bpl);
  123. *(rp++) = cpu_to_le32(databuf_phys_addr + offset);
  124. *(rp++) = cpu_to_le32(0); /* bits 63-32 */
  125. if ((lines <= NTSC_FIELD_HEIGHT)
  126. || (line < (NTSC_FIELD_HEIGHT - 1)) || !(out->is_60hz))
  127. /* to skip the other field line */
  128. offset += dist_betwn_starts;
  129. /* check if we need to enable the FIFO after the first 4 lines
  130. * For the upstream video channel, the risc engine will enable
  131. * the FIFO. */
  132. if (fifo_enable && line == 3) {
  133. *(rp++) = cpu_to_le32(RISC_WRITECR);
  134. *(rp++) = cpu_to_le32(sram_ch->dma_ctl);
  135. *(rp++) = cpu_to_le32(FLD_VID_FIFO_EN);
  136. *(rp++) = cpu_to_le32(0x00000001);
  137. }
  138. }
  139. return rp;
  140. }
  141. static int cx25821_risc_buffer_upstream(struct cx25821_channel *chan,
  142. struct pci_dev *pci,
  143. unsigned int top_offset,
  144. unsigned int bpl, unsigned int lines)
  145. {
  146. struct cx25821_video_out_data *out = chan->out;
  147. __le32 *rp;
  148. int fifo_enable = 0;
  149. /* get line count for single field */
  150. int singlefield_lines = lines >> 1;
  151. int odd_num_lines = singlefield_lines;
  152. int frame = 0;
  153. int frame_size = 0;
  154. int databuf_offset = 0;
  155. int risc_program_size = 0;
  156. int risc_flag = RISC_CNT_RESET;
  157. unsigned int bottom_offset = bpl;
  158. dma_addr_t risc_phys_jump_addr;
  159. if (out->is_60hz) {
  160. odd_num_lines = singlefield_lines + 1;
  161. risc_program_size = FRAME1_VID_PROG_SIZE;
  162. frame_size = (bpl == Y411_LINE_SZ) ?
  163. FRAME_SIZE_NTSC_Y411 : FRAME_SIZE_NTSC_Y422;
  164. } else {
  165. risc_program_size = PAL_VID_PROG_SIZE;
  166. frame_size = (bpl == Y411_LINE_SZ) ?
  167. FRAME_SIZE_PAL_Y411 : FRAME_SIZE_PAL_Y422;
  168. }
  169. /* Virtual address of Risc buffer program */
  170. rp = out->_dma_virt_addr;
  171. for (frame = 0; frame < NUM_FRAMES; frame++) {
  172. databuf_offset = frame_size * frame;
  173. if (UNSET != top_offset) {
  174. fifo_enable = (frame == 0) ? FIFO_ENABLE : FIFO_DISABLE;
  175. rp = cx25821_risc_field_upstream(chan, rp,
  176. out->_data_buf_phys_addr +
  177. databuf_offset, top_offset, 0, bpl,
  178. odd_num_lines, fifo_enable, ODD_FIELD);
  179. }
  180. fifo_enable = FIFO_DISABLE;
  181. /* Even Field */
  182. rp = cx25821_risc_field_upstream(chan, rp,
  183. out->_data_buf_phys_addr +
  184. databuf_offset, bottom_offset,
  185. 0x200, bpl, singlefield_lines,
  186. fifo_enable, EVEN_FIELD);
  187. if (frame == 0) {
  188. risc_flag = RISC_CNT_RESET;
  189. risc_phys_jump_addr = out->_dma_phys_start_addr +
  190. risc_program_size;
  191. } else {
  192. risc_phys_jump_addr = out->_dma_phys_start_addr;
  193. risc_flag = RISC_CNT_INC;
  194. }
  195. /* Loop to 2ndFrameRISC or to Start of Risc
  196. * program & generate IRQ
  197. */
  198. *(rp++) = cpu_to_le32(RISC_JUMP | RISC_IRQ1 | risc_flag);
  199. *(rp++) = cpu_to_le32(risc_phys_jump_addr);
  200. *(rp++) = cpu_to_le32(0);
  201. }
  202. return 0;
  203. }
  204. void cx25821_stop_upstream_video(struct cx25821_channel *chan)
  205. {
  206. struct cx25821_video_out_data *out = chan->out;
  207. struct cx25821_dev *dev = chan->dev;
  208. const struct sram_channel *sram_ch = chan->sram_channels;
  209. u32 tmp = 0;
  210. if (!out->_is_running) {
  211. pr_info("No video file is currently running so return!\n");
  212. return;
  213. }
  214. /* Set the interrupt mask register, disable irq. */
  215. cx_set(PCI_INT_MSK, cx_read(PCI_INT_MSK) & ~(1 << sram_ch->irq_bit));
  216. /* Disable RISC interrupts */
  217. tmp = cx_read(sram_ch->int_msk);
  218. cx_write(sram_ch->int_msk, tmp & ~_intr_msk);
  219. /* Turn OFF risc and fifo enable */
  220. tmp = cx_read(sram_ch->dma_ctl);
  221. cx_write(sram_ch->dma_ctl, tmp & ~(FLD_VID_FIFO_EN | FLD_VID_RISC_EN));
  222. free_irq(dev->pci->irq, chan);
  223. /* Clear data buffer memory */
  224. if (out->_data_buf_virt_addr)
  225. memset(out->_data_buf_virt_addr, 0, out->_data_buf_size);
  226. out->_is_running = 0;
  227. out->_is_first_frame = 0;
  228. out->_frame_count = 0;
  229. out->_file_status = END_OF_FILE;
  230. tmp = cx_read(VID_CH_MODE_SEL);
  231. cx_write(VID_CH_MODE_SEL, tmp & 0xFFFFFE00);
  232. }
  233. void cx25821_free_mem_upstream(struct cx25821_channel *chan)
  234. {
  235. struct cx25821_video_out_data *out = chan->out;
  236. struct cx25821_dev *dev = chan->dev;
  237. if (out->_is_running)
  238. cx25821_stop_upstream_video(chan);
  239. if (out->_dma_virt_addr) {
  240. pci_free_consistent(dev->pci, out->_risc_size,
  241. out->_dma_virt_addr, out->_dma_phys_addr);
  242. out->_dma_virt_addr = NULL;
  243. }
  244. if (out->_data_buf_virt_addr) {
  245. pci_free_consistent(dev->pci, out->_data_buf_size,
  246. out->_data_buf_virt_addr,
  247. out->_data_buf_phys_addr);
  248. out->_data_buf_virt_addr = NULL;
  249. }
  250. }
  251. int cx25821_write_frame(struct cx25821_channel *chan,
  252. const char __user *data, size_t count)
  253. {
  254. struct cx25821_video_out_data *out = chan->out;
  255. int line_size = (out->_pixel_format == PIXEL_FRMT_411) ?
  256. Y411_LINE_SZ : Y422_LINE_SZ;
  257. int frame_size = 0;
  258. int frame_offset = 0;
  259. int curpos = out->curpos;
  260. if (out->is_60hz)
  261. frame_size = (line_size == Y411_LINE_SZ) ?
  262. FRAME_SIZE_NTSC_Y411 : FRAME_SIZE_NTSC_Y422;
  263. else
  264. frame_size = (line_size == Y411_LINE_SZ) ?
  265. FRAME_SIZE_PAL_Y411 : FRAME_SIZE_PAL_Y422;
  266. if (curpos == 0) {
  267. out->cur_frame_index = out->_frame_index;
  268. if (wait_event_interruptible(out->waitq, out->cur_frame_index != out->_frame_index))
  269. return -EINTR;
  270. out->cur_frame_index = out->_frame_index;
  271. }
  272. frame_offset = out->cur_frame_index ? frame_size : 0;
  273. if (frame_size - curpos < count)
  274. count = frame_size - curpos;
  275. if (copy_from_user((__force char *)out->_data_buf_virt_addr + frame_offset + curpos,
  276. data, count))
  277. return -EFAULT;
  278. curpos += count;
  279. if (curpos == frame_size) {
  280. out->_frame_count++;
  281. curpos = 0;
  282. }
  283. out->curpos = curpos;
  284. return count;
  285. }
  286. static int cx25821_upstream_buffer_prepare(struct cx25821_channel *chan,
  287. const struct sram_channel *sram_ch,
  288. int bpl)
  289. {
  290. struct cx25821_video_out_data *out = chan->out;
  291. struct cx25821_dev *dev = chan->dev;
  292. int ret = 0;
  293. dma_addr_t dma_addr;
  294. dma_addr_t data_dma_addr;
  295. if (out->_dma_virt_addr != NULL)
  296. pci_free_consistent(dev->pci, out->upstream_riscbuf_size,
  297. out->_dma_virt_addr, out->_dma_phys_addr);
  298. out->_dma_virt_addr = pci_alloc_consistent(dev->pci,
  299. out->upstream_riscbuf_size, &dma_addr);
  300. out->_dma_virt_start_addr = out->_dma_virt_addr;
  301. out->_dma_phys_start_addr = dma_addr;
  302. out->_dma_phys_addr = dma_addr;
  303. out->_risc_size = out->upstream_riscbuf_size;
  304. if (!out->_dma_virt_addr) {
  305. pr_err("FAILED to allocate memory for Risc buffer! Returning\n");
  306. return -ENOMEM;
  307. }
  308. /* Clear memory at address */
  309. memset(out->_dma_virt_addr, 0, out->_risc_size);
  310. if (out->_data_buf_virt_addr != NULL)
  311. pci_free_consistent(dev->pci, out->upstream_databuf_size,
  312. out->_data_buf_virt_addr,
  313. out->_data_buf_phys_addr);
  314. /* For Video Data buffer allocation */
  315. out->_data_buf_virt_addr = pci_alloc_consistent(dev->pci,
  316. out->upstream_databuf_size, &data_dma_addr);
  317. out->_data_buf_phys_addr = data_dma_addr;
  318. out->_data_buf_size = out->upstream_databuf_size;
  319. if (!out->_data_buf_virt_addr) {
  320. pr_err("FAILED to allocate memory for data buffer! Returning\n");
  321. return -ENOMEM;
  322. }
  323. /* Clear memory at address */
  324. memset(out->_data_buf_virt_addr, 0, out->_data_buf_size);
  325. /* Create RISC programs */
  326. ret = cx25821_risc_buffer_upstream(chan, dev->pci, 0, bpl,
  327. out->_lines_count);
  328. if (ret < 0) {
  329. pr_info("Failed creating Video Upstream Risc programs!\n");
  330. goto error;
  331. }
  332. return 0;
  333. error:
  334. return ret;
  335. }
  336. static int cx25821_video_upstream_irq(struct cx25821_channel *chan, u32 status)
  337. {
  338. struct cx25821_video_out_data *out = chan->out;
  339. struct cx25821_dev *dev = chan->dev;
  340. u32 int_msk_tmp;
  341. const struct sram_channel *channel = chan->sram_channels;
  342. int singlefield_lines = NTSC_FIELD_HEIGHT;
  343. int line_size_in_bytes = Y422_LINE_SZ;
  344. int odd_risc_prog_size = 0;
  345. dma_addr_t risc_phys_jump_addr;
  346. __le32 *rp;
  347. if (status & FLD_VID_SRC_RISC1) {
  348. /* We should only process one program per call */
  349. u32 prog_cnt = cx_read(channel->gpcnt);
  350. /* Since we've identified our IRQ, clear our bits from the
  351. * interrupt mask and interrupt status registers */
  352. int_msk_tmp = cx_read(channel->int_msk);
  353. cx_write(channel->int_msk, int_msk_tmp & ~_intr_msk);
  354. cx_write(channel->int_stat, _intr_msk);
  355. wake_up(&out->waitq);
  356. spin_lock(&dev->slock);
  357. out->_frame_index = prog_cnt;
  358. if (out->_is_first_frame) {
  359. out->_is_first_frame = 0;
  360. if (out->is_60hz) {
  361. singlefield_lines += 1;
  362. odd_risc_prog_size = ODD_FLD_NTSC_PROG_SIZE;
  363. } else {
  364. singlefield_lines = PAL_FIELD_HEIGHT;
  365. odd_risc_prog_size = ODD_FLD_PAL_PROG_SIZE;
  366. }
  367. if (out->_dma_virt_start_addr != NULL) {
  368. line_size_in_bytes =
  369. (out->_pixel_format ==
  370. PIXEL_FRMT_411) ? Y411_LINE_SZ :
  371. Y422_LINE_SZ;
  372. risc_phys_jump_addr =
  373. out->_dma_phys_start_addr +
  374. odd_risc_prog_size;
  375. rp = cx25821_update_riscprogram(chan,
  376. out->_dma_virt_start_addr, TOP_OFFSET,
  377. line_size_in_bytes, 0x0,
  378. singlefield_lines, FIFO_DISABLE,
  379. ODD_FIELD);
  380. /* Jump to Even Risc program of 1st Frame */
  381. *(rp++) = cpu_to_le32(RISC_JUMP);
  382. *(rp++) = cpu_to_le32(risc_phys_jump_addr);
  383. *(rp++) = cpu_to_le32(0);
  384. }
  385. }
  386. spin_unlock(&dev->slock);
  387. } else {
  388. if (status & FLD_VID_SRC_UF)
  389. pr_err("%s(): Video Received Underflow Error Interrupt!\n",
  390. __func__);
  391. if (status & FLD_VID_SRC_SYNC)
  392. pr_err("%s(): Video Received Sync Error Interrupt!\n",
  393. __func__);
  394. if (status & FLD_VID_SRC_OPC_ERR)
  395. pr_err("%s(): Video Received OpCode Error Interrupt!\n",
  396. __func__);
  397. }
  398. if (out->_file_status == END_OF_FILE) {
  399. pr_err("EOF Channel 1 Framecount = %d\n", out->_frame_count);
  400. return -1;
  401. }
  402. /* ElSE, set the interrupt mask register, re-enable irq. */
  403. int_msk_tmp = cx_read(channel->int_msk);
  404. cx_write(channel->int_msk, int_msk_tmp |= _intr_msk);
  405. return 0;
  406. }
  407. static irqreturn_t cx25821_upstream_irq(int irq, void *dev_id)
  408. {
  409. struct cx25821_channel *chan = dev_id;
  410. struct cx25821_dev *dev = chan->dev;
  411. u32 vid_status;
  412. int handled = 0;
  413. const struct sram_channel *sram_ch;
  414. if (!dev)
  415. return -1;
  416. sram_ch = chan->sram_channels;
  417. vid_status = cx_read(sram_ch->int_stat);
  418. /* Only deal with our interrupt */
  419. if (vid_status)
  420. handled = cx25821_video_upstream_irq(chan, vid_status);
  421. return IRQ_RETVAL(handled);
  422. }
  423. static void cx25821_set_pixelengine(struct cx25821_channel *chan,
  424. const struct sram_channel *ch,
  425. int pix_format)
  426. {
  427. struct cx25821_video_out_data *out = chan->out;
  428. struct cx25821_dev *dev = chan->dev;
  429. int width = WIDTH_D1;
  430. int height = out->_lines_count;
  431. int num_lines, odd_num_lines;
  432. u32 value;
  433. int vip_mode = OUTPUT_FRMT_656;
  434. value = ((pix_format & 0x3) << 12) | (vip_mode & 0x7);
  435. value &= 0xFFFFFFEF;
  436. value |= out->is_60hz ? 0 : 0x10;
  437. cx_write(ch->vid_fmt_ctl, value);
  438. /* set number of active pixels in each line.
  439. * Default is 720 pixels in both NTSC and PAL format */
  440. cx_write(ch->vid_active_ctl1, width);
  441. num_lines = (height / 2) & 0x3FF;
  442. odd_num_lines = num_lines;
  443. if (out->is_60hz)
  444. odd_num_lines += 1;
  445. value = (num_lines << 16) | odd_num_lines;
  446. /* set number of active lines in field 0 (top) and field 1 (bottom) */
  447. cx_write(ch->vid_active_ctl2, value);
  448. cx_write(ch->vid_cdt_size, VID_CDT_SIZE >> 3);
  449. }
  450. static int cx25821_start_video_dma_upstream(struct cx25821_channel *chan,
  451. const struct sram_channel *sram_ch)
  452. {
  453. struct cx25821_video_out_data *out = chan->out;
  454. struct cx25821_dev *dev = chan->dev;
  455. u32 tmp = 0;
  456. int err = 0;
  457. /* 656/VIP SRC Upstream Channel I & J and 7 - Host Bus Interface for
  458. * channel A-C
  459. */
  460. tmp = cx_read(VID_CH_MODE_SEL);
  461. cx_write(VID_CH_MODE_SEL, tmp | 0x1B0001FF);
  462. /* Set the physical start address of the RISC program in the initial
  463. * program counter(IPC) member of the cmds.
  464. */
  465. cx_write(sram_ch->cmds_start + 0, out->_dma_phys_addr);
  466. /* Risc IPC High 64 bits 63-32 */
  467. cx_write(sram_ch->cmds_start + 4, 0);
  468. /* reset counter */
  469. cx_write(sram_ch->gpcnt_ctl, 3);
  470. /* Clear our bits from the interrupt status register. */
  471. cx_write(sram_ch->int_stat, _intr_msk);
  472. /* Set the interrupt mask register, enable irq. */
  473. cx_set(PCI_INT_MSK, cx_read(PCI_INT_MSK) | (1 << sram_ch->irq_bit));
  474. tmp = cx_read(sram_ch->int_msk);
  475. cx_write(sram_ch->int_msk, tmp |= _intr_msk);
  476. err = request_irq(dev->pci->irq, cx25821_upstream_irq,
  477. IRQF_SHARED, dev->name, chan);
  478. if (err < 0) {
  479. pr_err("%s: can't get upstream IRQ %d\n",
  480. dev->name, dev->pci->irq);
  481. goto fail_irq;
  482. }
  483. /* Start the DMA engine */
  484. tmp = cx_read(sram_ch->dma_ctl);
  485. cx_set(sram_ch->dma_ctl, tmp | FLD_VID_RISC_EN);
  486. out->_is_running = 1;
  487. out->_is_first_frame = 1;
  488. return 0;
  489. fail_irq:
  490. cx25821_dev_unregister(dev);
  491. return err;
  492. }
  493. int cx25821_vidupstream_init(struct cx25821_channel *chan,
  494. int pixel_format)
  495. {
  496. struct cx25821_video_out_data *out = chan->out;
  497. struct cx25821_dev *dev = chan->dev;
  498. const struct sram_channel *sram_ch;
  499. u32 tmp;
  500. int err = 0;
  501. int data_frame_size = 0;
  502. int risc_buffer_size = 0;
  503. if (out->_is_running) {
  504. pr_info("Video Channel is still running so return!\n");
  505. return 0;
  506. }
  507. sram_ch = chan->sram_channels;
  508. out->is_60hz = dev->tvnorm & V4L2_STD_525_60;
  509. /* 656/VIP SRC Upstream Channel I & J and 7 - Host Bus Interface for
  510. * channel A-C
  511. */
  512. tmp = cx_read(VID_CH_MODE_SEL);
  513. cx_write(VID_CH_MODE_SEL, tmp | 0x1B0001FF);
  514. out->_is_running = 0;
  515. out->_frame_count = 0;
  516. out->_file_status = RESET_STATUS;
  517. out->_lines_count = out->is_60hz ? 480 : 576;
  518. out->_pixel_format = pixel_format;
  519. out->_line_size = (out->_pixel_format == PIXEL_FRMT_422) ?
  520. (WIDTH_D1 * 2) : (WIDTH_D1 * 3) / 2;
  521. data_frame_size = out->is_60hz ? NTSC_DATA_BUF_SZ : PAL_DATA_BUF_SZ;
  522. risc_buffer_size = out->is_60hz ?
  523. NTSC_RISC_BUF_SIZE : PAL_RISC_BUF_SIZE;
  524. out->_is_running = 0;
  525. out->_frame_count = 0;
  526. out->_file_status = RESET_STATUS;
  527. out->_lines_count = out->is_60hz ? 480 : 576;
  528. out->_pixel_format = pixel_format;
  529. out->_line_size = (out->_pixel_format == PIXEL_FRMT_422) ?
  530. (WIDTH_D1 * 2) : (WIDTH_D1 * 3) / 2;
  531. out->curpos = 0;
  532. init_waitqueue_head(&out->waitq);
  533. err = cx25821_sram_channel_setup_upstream(dev, sram_ch,
  534. out->_line_size, 0);
  535. /* setup fifo + format */
  536. cx25821_set_pixelengine(chan, sram_ch, out->_pixel_format);
  537. out->upstream_riscbuf_size = risc_buffer_size * 2;
  538. out->upstream_databuf_size = data_frame_size * 2;
  539. /* Allocating buffers and prepare RISC program */
  540. err = cx25821_upstream_buffer_prepare(chan, sram_ch, out->_line_size);
  541. if (err < 0) {
  542. pr_err("%s: Failed to set up Video upstream buffers!\n",
  543. dev->name);
  544. goto error;
  545. }
  546. cx25821_start_video_dma_upstream(chan, sram_ch);
  547. return 0;
  548. error:
  549. cx25821_dev_unregister(dev);
  550. return err;
  551. }