日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

Hi3531与Hi3520 GPIO口的对比及驱动的修改

發布時間:2024/9/5 编程问答 34 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Hi3531与Hi3520 GPIO口的对比及驱动的修改 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

http://blog.csdn.net/xiangpingli/article/details/7251734

1、GPIO口的對比:

3520:

應用:16路CIF,4路、8路D1

管腳總數:768pin

GPIO: 8組,GPIO0~GPIO7

GPIO基地址:從NAND、NOR、DDR映射GPIOX寄存器地址都是一樣的:

3531:

應用:

單片:16D1+16CIF編碼+4D1解碼,8路D1同編同解,4路高清同編同解

???????? 雙片(+3532):16路D1同編同解,8路720P同編同解,4路1080P實時解碼

?管腳總數:817pin

GPIO:19組,GPIO0~GPIO18

?

3520與3531GPIO對比總結:

1、3531有19組GPIO,3520有8組GPIO,兩者GPIO0~7的地址是相同的。

2、各寄存器偏移地址不變

?

3520gpio驅動中針對3531修改:

1、首先把多出的寄存器組添加上,多了11組寄存器。

2、然后因為內核的接口變化了,修改ioctl相關的部分,記得unlocked_ioctl參數比原來的參數少了一個inode。

3、創建和初始化信號量的地方也要修改掉,DECLARE_MUTEX在linux3.0中也不存在了,取而代之的是DEFINE_SEMAPHORE

4、就是地址映射部分,哪里映射失敗,要把之前映射的全部釋放掉再退出:

?

hi_gpio.c:

#include <linux/module.h>
//#include <asm/hardware.h>
#include <linux/errno.h>
#include <linux/miscdevice.h>
#include <linux/fcntl.h>

#include <linux/init.h>
#include <linux/delay.h>
#include <linux/proc_fs.h>
#include <linux/workqueue.h>

#include <asm/uaccess.h>
#include <asm/system.h>
#include <asm/io.h>
#include "hi_gpio.h"

#define? GPIO_0_BASE_ADDR? 0x20150000
#define? GPIO_1_BASE_ADDR? 0x20160000
#define? GPIO_2_BASE_ADDR? 0x20170000
#define? GPIO_3_BASE_ADDR? 0x20180000
#define? GPIO_4_BASE_ADDR? 0x20190000
#define? GPIO_5_BASE_ADDR? 0x201a0000
#define? GPIO_6_BASE_ADDR? 0x201b0000
#define? GPIO_7_BASE_ADDR? 0x201c0000
#define? GPIO_8_BASE_ADDR? 0x201d0000
/*??changed for 3531??*/
#define? GPIO_9_BASE_ADDR? 0x201e0000
#define? GPIO_10_BASE_ADDR? 0x201f0000
#define? GPIO_11_BASE_ADDR? 0x20200000
#define? GPIO_12_BASE_ADDR? 0x20210000
#define? GPIO_13_BASE_ADDR? 0x20220000
#define? GPIO_14_BASE_ADDR? 0x20230000
#define? GPIO_15_BASE_ADDR? 0x20240000
#define? GPIO_16_BASE_ADDR? 0x20250000
#define? GPIO_17_BASE_ADDR? 0x20260000
#define? GPIO_18_BASE_ADDR? 0x20270000


#define? GPIO_DIR_BASE?? (groupbase+0x400)
#define? GPIO_INTR_MASK? (groupbase+0x410)
#define? GPIO_DATA_BASE?? data_reg_base


#define WRITE_REG(Addr, Value) ((*(volatile unsigned int *)(Addr)) = (Value))
#define READ_REG(Addr)???????? (*(volatile unsigned int *)(Addr))


static DEFINE_SEMAPHORE(gpio_sem);? /* 根據linux3.0.y 的源碼,DEFINE_SEMAPHORE取代了DECLARE_MUTEX */

//static DECLARE_MUTEX(gpio_sem);

unsigned int groupbase=-1;
unsigned int data_reg_base=0;
unsigned int gpio_0_base_addr_virtual=0;
unsigned int gpio_1_base_addr_virtual=0;
unsigned int gpio_2_base_addr_virtual=0;
unsigned int gpio_3_base_addr_virtual=0;
unsigned int gpio_4_base_addr_virtual=0;
unsigned int gpio_5_base_addr_virtual=0;
unsigned int gpio_6_base_addr_virtual=0;
unsigned int gpio_7_base_addr_virtual=0;
unsigned int gpio_8_base_addr_virtual=0;
unsigned int gpio_9_base_addr_virtual=0;
unsigned int gpio_10_base_addr_virtual=0;
unsigned int gpio_11_base_addr_virtual=0;
unsigned int gpio_12_base_addr_virtual=0;
unsigned int gpio_13_base_addr_virtual=0;
unsigned int gpio_14_base_addr_virtual=0;
unsigned int gpio_15_base_addr_virtual=0;
unsigned int gpio_16_base_addr_virtual=0;
unsigned int gpio_17_base_addr_virtual=0;
unsigned int gpio_18_base_addr_virtual=0;


static void gpio_calculate_data_groupbase(unsigned int groupnum, unsigned int bitnum)
{
??? switch(groupnum)
??? {
?case 0:?
????? groupbase =gpio_0_base_addr_virtual;
????? break;
?case 1:?
????? groupbase =gpio_1_base_addr_virtual;
????? break;
?case 2:?
????? groupbase =gpio_2_base_addr_virtual;
????? break;
?case 3:?
????? groupbase =gpio_3_base_addr_virtual;
????? break;
?case 4:?
????? groupbase =gpio_4_base_addr_virtual;
????? break;
?case 5:?
????? groupbase =gpio_5_base_addr_virtual;
????? break;
?case 6:?
????? groupbase =gpio_6_base_addr_virtual;
????? break;
?case 7:?
????? groupbase =gpio_7_base_addr_virtual;
????? break;
?case 8:?
????? groupbase =gpio_8_base_addr_virtual;
????? break;
?case 9:?
????? groupbase =gpio_9_base_addr_virtual;
????? break;
?case 10:?
????? groupbase =gpio_10_base_addr_virtual;
????? break;
?case 11:?
????? groupbase =gpio_11_base_addr_virtual;
????? break;
?case 12:?
????? groupbase =gpio_12_base_addr_virtual;
????? break;
?case 13:?
????? groupbase =gpio_13_base_addr_virtual;
????? break;
?case 14:?
????? groupbase =gpio_14_base_addr_virtual;
????? break;
?case 15:?
????? groupbase =gpio_15_base_addr_virtual;
????? break;
?case 16:?
????? groupbase =gpio_16_base_addr_virtual;
????? break;
?case 17:?
????? groupbase =gpio_17_base_addr_virtual;
????? break;
?case 18:?
????? groupbase =gpio_18_base_addr_virtual;
????? break;


???
?default:
????? break;
??? }

//??? printk("groupbase:%x !\n",groupbase);
??? data_reg_base=groupbase+(1<<(bitnum+2));
//??? printk("data_reg_base:%x !\n",data_reg_base);
}

?

static int gpio_open(struct inode *inode, struct file *filp)
{
?? return 0;??
}

static int gpio_release(struct inode *inode, struct file *filp)
{
?return 0;?
}


//static int gpio_ioctl(struct inode *inode, struct file *filp, unsigned int cmd, unsigned long arg)
static int gpio_ioctl(struct file *filp, unsigned int cmd, unsigned long arg)
{?????????

??? //這里代碼沒改

??? return 0;

}


static struct file_operations gpio_fops = {
? owner:THIS_MODULE,
? open:gpio_open,
?// ioctl:gpio_ioctl,
? unlocked_ioctl:gpio_ioctl,??/*?linux3.0.y 不再使用ioctl,采用unlocked_ioctl */
? release:gpio_release,
};

static struct miscdevice gpio_dev = {
??? MISC_DYNAMIC_MINOR,
??? "hi_gpio",
??? &gpio_fops,
};

?

//gpio的復用關系要放在uboot下面;
static int __init hi_gpio_init(void)
{
?signed int? ret=0;

??????? ret = misc_register(&gpio_dev);
??????? if (ret)
??????? {
??????????????? printk(KERN_ERR "register misc dev for hi_gpio fail!\n");
??return ret;
?}
?
?gpio_0_base_addr_virtual=(unsigned int)ioremap_nocache(GPIO_0_BASE_ADDR,0x40000);
?if(!gpio_0_base_addr_virtual)
?{
???? printk("ioremap gpio group0 failed!\n");
???? return -1;
?}
?gpio_1_base_addr_virtual=gpio_0_base_addr_virtual+0x10000;
?gpio_2_base_addr_virtual=gpio_0_base_addr_virtual+0x20000;
?gpio_3_base_addr_virtual=gpio_0_base_addr_virtual+0x30000;
?gpio_4_base_addr_virtual=(unsigned int) ioremap_nocache(GPIO_4_BASE_ADDR,0x40000);
?if(!gpio_4_base_addr_virtual)
?{
???? printk("ioremap gpio group0 failed!\n");
??/*說明gpio_0 映射成功了,但gpio_4沒成功,所以要把gpio_0的釋放掉*/
???? iounmap((void*)gpio_0_base_addr_virtual);
???? return -1;
?}

?gpio_5_base_addr_virtual=gpio_4_base_addr_virtual+0x10000;
?gpio_6_base_addr_virtual=gpio_4_base_addr_virtual+0x20000;
?gpio_7_base_addr_virtual=gpio_4_base_addr_virtual+0x30000;

?gpio_8_base_addr_virtual=(unsigned int) ioremap_nocache(GPIO_8_BASE_ADDR,0x40000);
?if(!gpio_8_base_addr_virtual)
?{
???? printk("ioremap gpio group0 failed!\n");
??/*說明gpio_0 和gpio_4都映射成功了,但gpio_8沒映射成功,所以將之前映射的釋放*/
???? iounmap((void*)gpio_0_base_addr_virtual);
???? iounmap((void*)gpio_4_base_addr_virtual);???
???? return -1;
?}

?gpio_9_base_addr_virtual?? = gpio_8_base_addr_virtual + 0x10000;
?gpio_10_base_addr_virtual = gpio_8_base_addr_virtual + 0x20000;
?gpio_11_base_addr_virtual = gpio_8_base_addr_virtual + 0x30000;

?gpio_12_base_addr_virtual=(unsigned int) ioremap_nocache(GPIO_12_BASE_ADDR,0x40000);
?if(!gpio_12_base_addr_virtual)
?{
???? printk("ioremap gpio group0 failed!\n");
???? iounmap((void*)gpio_0_base_addr_virtual);???
???? iounmap((void*)gpio_4_base_addr_virtual);?
???? iounmap((void*)gpio_8_base_addr_virtual);?
???? return -1;
?}

?gpio_13_base_addr_virtual?? = gpio_12_base_addr_virtual + 0x10000;
?gpio_14_base_addr_virtual = gpio_12_base_addr_virtual + 0x20000;
?gpio_15_base_addr_virtual = gpio_12_base_addr_virtual + 0x30000;

?gpio_16_base_addr_virtual=(unsigned int) ioremap_nocache(GPIO_16_BASE_ADDR,0x30000); /* 注意:這里不能再是0x40000了*/
?if(!gpio_16_base_addr_virtual)
?{
???? printk("ioremap gpio group0 failed!\n");????

???? iounmap((void*)gpio_0_base_addr_virtual);???
???? iounmap((void*)gpio_4_base_addr_virtual);?
???? iounmap((void*)gpio_8_base_addr_virtual);?
???? iounmap((void*)gpio_12_base_addr_virtual);?
???? return -1;
?}

?gpio_17_base_addr_virtual?? = gpio_16_base_addr_virtual + 0x10000;
?gpio_18_base_addr_virtual = gpio_16_base_addr_virtual + 0x20000;

?

?return 0;?????????
}


static void __exit hi_gpio_exit(void)
{
??? misc_deregister(&gpio_dev);
??? iounmap((void*)gpio_0_base_addr_virtual);
??? iounmap((void*)gpio_4_base_addr_virtual);
??? iounmap((void*)gpio_8_base_addr_virtual);
??? iounmap((void*)gpio_12_base_addr_virtual);
??? iounmap((void*)gpio_16_base_addr_virtual);?

}

module_init(hi_gpio_init);
module_exit(hi_gpio_exit);

MODULE_AUTHOR("Digital Media Team ,Hisilicon crop ");
MODULE_LICENSE("GPL");
MODULE_DESCRIPTION("Real Time Clock interface for HI3511");?


?


總結

以上是生活随笔為你收集整理的Hi3531与Hi3520 GPIO口的对比及驱动的修改的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。