Mercurial > pt1
comparison driver/pt1_pci.c @ 40:8f30a05cded2
imported patch dmactlalloc
author | Yoshiki Yazawa <yaz@honeyplanet.jp> |
---|---|
date | Tue, 28 Apr 2009 17:16:48 +0900 |
parents | c359e7adf700 |
children | 51a006a8d843 |
comparison
equal
deleted
inserted
replaced
39:b03685d25fee | 40:8f30a05cded2 |
---|---|
68 | 68 |
69 #define PACKET_SIZE 188 // 1パケット長 | 69 #define PACKET_SIZE 188 // 1パケット長 |
70 #define MAX_READ_BLOCK 4 // 1度に読み出す最大DMAバッファ数 | 70 #define MAX_READ_BLOCK 4 // 1度に読み出す最大DMAバッファ数 |
71 #define MAX_PCI_DEVICE 128 // 最大64枚 | 71 #define MAX_PCI_DEVICE 128 // 最大64枚 |
72 #define DMA_SIZE 4096 // DMAバッファサイズ | 72 #define DMA_SIZE 4096 // DMAバッファサイズ |
73 #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,22) | |
74 #define DMA_RING_SIZE 128 // RINGサイズ | 73 #define DMA_RING_SIZE 128 // RINGサイズ |
75 #define DMA_RING_MAX 511 // 1RINGにいくつ詰めるか(1023はNGで511まで) | 74 #define DMA_RING_MAX 511 // 1RINGにいくつ詰めるか(1023はNGで511まで) |
75 #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,22) | |
76 #define CHANEL_DMA_SIZE (2*1024*1024) // 地デジ用(16Mbps) | 76 #define CHANEL_DMA_SIZE (2*1024*1024) // 地デジ用(16Mbps) |
77 #define BS_CHANEL_DMA_SIZE (4*1024*1024) // BS用(32Mbps) | 77 #define BS_CHANEL_DMA_SIZE (4*1024*1024) // BS用(32Mbps) |
78 #else | 78 #else |
79 #define DMA_RING_SIZE 28 // RINGサイズ | 79 #define CHANEL_DMA_SIZE (1*128*1024) // 地デジ用(1Mbps) |
80 #define DMA_RING_MAX 511 // 1RINGにいくつ詰めるか(1023はNGで511まで) | 80 #define BS_CHANEL_DMA_SIZE (1*128*1024) // BS用(1Mbps) |
81 #define CHANEL_DMA_SIZE (1*128*1024) // 地デジ用(16Mbps) | |
82 #define BS_CHANEL_DMA_SIZE (1*128*1024) // BS用(32Mbps) | |
83 #endif | 81 #endif |
84 | 82 |
85 typedef struct _DMA_CONTROL{ | 83 typedef struct _DMA_CONTROL{ |
86 dma_addr_t ring_dma[DMA_RING_MAX] ; // DMA情報 | 84 dma_addr_t ring_dma[DMA_RING_MAX] ; // DMA情報 |
87 __u32 *data[DMA_RING_MAX]; | 85 __u32 *data[DMA_RING_MAX]; |
100 dev_t dev ; | 98 dev_t dev ; |
101 int card_number; | 99 int card_number; |
102 __u32 base_minor ; | 100 __u32 base_minor ; |
103 struct cdev cdev[MAX_CHANNEL]; | 101 struct cdev cdev[MAX_CHANNEL]; |
104 wait_queue_head_t dma_wait_q ;// for poll on reading | 102 wait_queue_head_t dma_wait_q ;// for poll on reading |
105 DMA_CONTROL dmactl[DMA_RING_SIZE]; | 103 DMA_CONTROL *dmactl[DMA_RING_SIZE]; |
106 PT1_CHANNEL *channel[MAX_CHANNEL]; | 104 PT1_CHANNEL *channel[MAX_CHANNEL]; |
107 }PT1_DEVICE; | 105 }PT1_DEVICE; |
108 | 106 |
109 typedef struct _MICRO_PACKET{ | 107 typedef struct _MICRO_PACKET{ |
110 char data[3]; | 108 char data[3]; |
155 __u32 *dataptr ; | 153 __u32 *dataptr ; |
156 | 154 |
157 // データ初期化 | 155 // データ初期化 |
158 for(ring_pos = 0 ; ring_pos < DMA_RING_SIZE ; ring_pos++){ | 156 for(ring_pos = 0 ; ring_pos < DMA_RING_SIZE ; ring_pos++){ |
159 for(data_pos = 0 ; data_pos < DMA_RING_MAX ; data_pos++){ | 157 for(data_pos = 0 ; data_pos < DMA_RING_MAX ; data_pos++){ |
160 dataptr = dev_conf->dmactl[ring_pos].data[data_pos]; | 158 dataptr = (dev_conf->dmactl[ring_pos])->data[data_pos]; |
161 dataptr[(DMA_SIZE / sizeof(__u32)) - 2] = 0; | 159 dataptr[(DMA_SIZE / sizeof(__u32)) - 2] = 0; |
162 } | 160 } |
163 } | 161 } |
164 // 転送カウンタをリセット | 162 // 転送カウンタをリセット |
165 writel(0x00000010, dev_conf->regs); | 163 writel(0x00000010, dev_conf->regs); |
203 if(kthread_should_stop()){ | 201 if(kthread_should_stop()){ |
204 break ; | 202 break ; |
205 } | 203 } |
206 | 204 |
207 for(;;){ | 205 for(;;){ |
208 dataptr = dev_conf->dmactl[ring_pos].data[data_pos]; | 206 dataptr = (dev_conf->dmactl[ring_pos])->data[data_pos]; |
209 // データあり? | 207 // データあり? |
210 if(dataptr[(DMA_SIZE / sizeof(__u32)) - 2] == 0){ | 208 if(dataptr[(DMA_SIZE / sizeof(__u32)) - 2] == 0){ |
211 break ; | 209 break ; |
212 } | 210 } |
213 micro.val = *dataptr ; | 211 micro.val = *dataptr ; |
537 } | 535 } |
538 addr >>= 12 ; | 536 addr >>= 12 ; |
539 memcpy(ptr, &addr, sizeof(__u32)); | 537 memcpy(ptr, &addr, sizeof(__u32)); |
540 ptr += 1 ; | 538 ptr += 1 ; |
541 | 539 |
542 dmactl = &dev_conf->dmactl[lp]; | 540 dmactl = dev_conf->dmactl[lp]; |
543 for(lp2 = 0 ; lp2 < DMA_RING_MAX ; lp2++){ | 541 for(lp2 = 0 ; lp2 < DMA_RING_MAX ; lp2++){ |
544 dmaptr = pci_alloc_consistent(pdev, DMA_SIZE, &dmactl->ring_dma[lp2]); | 542 dmaptr = pci_alloc_consistent(pdev, DMA_SIZE, &dmactl->ring_dma[lp2]); |
545 if(dmaptr == NULL){ | 543 if(dmaptr == NULL){ |
546 printk(KERN_INFO "PT1:DMA ALLOC ERROR\n"); | 544 printk(KERN_INFO "PT1:DMA ALLOC ERROR\n"); |
547 return -1 ; | 545 return -1 ; |
582 for(lp = 0 ; lp < DMA_RING_SIZE ; lp++){ | 580 for(lp = 0 ; lp < DMA_RING_SIZE ; lp++){ |
583 if(dev_conf->dmaptr[lp] != NULL){ | 581 if(dev_conf->dmaptr[lp] != NULL){ |
584 pci_free_consistent(pdev, DMA_SIZE, | 582 pci_free_consistent(pdev, DMA_SIZE, |
585 dev_conf->dmaptr[lp], dev_conf->ring_dma[lp]); | 583 dev_conf->dmaptr[lp], dev_conf->ring_dma[lp]); |
586 for(lp2 = 0 ; lp2 < DMA_RING_MAX ; lp2++){ | 584 for(lp2 = 0 ; lp2 < DMA_RING_MAX ; lp2++){ |
587 if(dev_conf->dmactl[lp].data[lp2] != NULL){ | 585 if((dev_conf->dmactl[lp])->data[lp2] != NULL){ |
588 pci_free_consistent(pdev, DMA_SIZE, | 586 pci_free_consistent(pdev, DMA_SIZE, |
589 dev_conf->dmactl[lp].data[lp2], | 587 (dev_conf->dmactl[lp])->data[lp2], |
590 dev_conf->dmactl[lp].ring_dma[lp2]); | 588 (dev_conf->dmactl[lp])->ring_dma[lp2]); |
591 } | 589 } |
592 } | 590 } |
593 } | 591 } |
594 } | 592 } |
595 return 0 ; | 593 return 0 ; |
601 int lp ; | 599 int lp ; |
602 int minor ; | 600 int minor ; |
603 u16 cmd ; | 601 u16 cmd ; |
604 PT1_DEVICE *dev_conf ; | 602 PT1_DEVICE *dev_conf ; |
605 PT1_CHANNEL *channel ; | 603 PT1_CHANNEL *channel ; |
604 int i; | |
606 struct resource *dummy; | 605 struct resource *dummy; |
607 | 606 |
608 rc = pci_enable_device(pdev); | 607 rc = pci_enable_device(pdev); |
609 if (rc) | 608 if (rc) |
610 return rc; | 609 return rc; |
628 | 627 |
629 dev_conf = kzalloc(sizeof(PT1_DEVICE), GFP_KERNEL); | 628 dev_conf = kzalloc(sizeof(PT1_DEVICE), GFP_KERNEL); |
630 if(!dev_conf){ | 629 if(!dev_conf){ |
631 printk(KERN_ERR "PT1:out of memory !"); | 630 printk(KERN_ERR "PT1:out of memory !"); |
632 return -ENOMEM ; | 631 return -ENOMEM ; |
632 } | |
633 for (i = 0; i < DMA_RING_SIZE; i++) { | |
634 dev_conf->dmactl[i] = kzalloc(sizeof(DMA_CONTROL), GFP_KERNEL); | |
635 if(!dev_conf->dmactl[i]){ | |
636 int j; | |
637 for (j = 0; j < i; j++) { | |
638 kfree(dev_conf->dmactl[j]); | |
639 } | |
640 kfree(dev_conf); | |
641 printk(KERN_ERR "PT1:out of memory !"); | |
642 return -ENOMEM ; | |
643 } | |
633 } | 644 } |
634 // PCIアドレスをマップする | 645 // PCIアドレスをマップする |
635 dev_conf->mmio_start = pci_resource_start(pdev, 0); | 646 dev_conf->mmio_start = pci_resource_start(pdev, 0); |
636 dev_conf->mmio_len = pci_resource_len(pdev, 0); | 647 dev_conf->mmio_len = pci_resource_len(pdev, 0); |
637 dummy = request_mem_region(dev_conf->mmio_start, dev_conf->mmio_len, DEV_NAME); | 648 dummy = request_mem_region(dev_conf->mmio_start, dev_conf->mmio_len, DEV_NAME); |
782 out_err_fpga: | 793 out_err_fpga: |
783 writel(0xb0b0000, dev_conf->regs); | 794 writel(0xb0b0000, dev_conf->regs); |
784 writel(0, dev_conf->regs + 4); | 795 writel(0, dev_conf->regs + 4); |
785 iounmap(dev_conf->regs); | 796 iounmap(dev_conf->regs); |
786 release_mem_region(dev_conf->mmio_start, dev_conf->mmio_len); | 797 release_mem_region(dev_conf->mmio_start, dev_conf->mmio_len); |
798 for (i = 0; i < DMA_RING_SIZE; i++) { | |
799 kfree(dev_conf->dmactl[i]); | |
800 } | |
787 kfree(dev_conf); | 801 kfree(dev_conf); |
788 out_err_regbase: | 802 out_err_regbase: |
789 return -EIO; | 803 return -EIO; |
790 | 804 |
791 } | 805 } |
794 { | 808 { |
795 | 809 |
796 int lp ; | 810 int lp ; |
797 __u32 val ; | 811 __u32 val ; |
798 PT1_DEVICE *dev_conf = (PT1_DEVICE *)pci_get_drvdata(pdev); | 812 PT1_DEVICE *dev_conf = (PT1_DEVICE *)pci_get_drvdata(pdev); |
813 int i; | |
799 | 814 |
800 if(dev_conf){ | 815 if(dev_conf){ |
801 if(dev_conf->kthread) { | 816 if(dev_conf->kthread) { |
802 kthread_stop(dev_conf->kthread); | 817 kthread_stop(dev_conf->kthread); |
803 dev_conf->kthread = NULL; | 818 dev_conf->kthread = NULL; |
828 writel(0xb0b0000, dev_conf->regs); | 843 writel(0xb0b0000, dev_conf->regs); |
829 writel(0, dev_conf->regs + 4); | 844 writel(0, dev_conf->regs + 4); |
830 settuner_reset(dev_conf->regs, LNB_OFF, TUNER_POWER_OFF); | 845 settuner_reset(dev_conf->regs, LNB_OFF, TUNER_POWER_OFF); |
831 release_mem_region(dev_conf->mmio_start, dev_conf->mmio_len); | 846 release_mem_region(dev_conf->mmio_start, dev_conf->mmio_len); |
832 iounmap(dev_conf->regs); | 847 iounmap(dev_conf->regs); |
848 for (i = 0; i < DMA_RING_SIZE; i++) { | |
849 kfree(dev_conf->dmactl[i]); | |
850 } | |
833 device[dev_conf->card_number] = NULL; | 851 device[dev_conf->card_number] = NULL; |
834 kfree(dev_conf); | 852 kfree(dev_conf); |
835 } | 853 } |
836 pci_set_drvdata(pdev, NULL); | 854 pci_set_drvdata(pdev, NULL); |
837 } | 855 } |