您的位置: OpenADSP社区论坛 -> Blackfin专区 -> 新手上路 -> ADSP开源下载发布区 -> Blackfin uClinux移植DM9000E
本帖共有1444个阅读者
发表帖子 发表投票 回复主题
Blackfin uClinux移植DM9000E
尊贵身份标志
andy(论坛版主)
andy
头衔:社区公民
帮派:无帮无派
帖数:2287
金钱:11132
积分:2263
注册时间:2011/6/8
楼主信息 | 留言 | Email | 主页 | 编辑 | 管理 | 离线
Blackfin uClinux移植DM9000E

1.参考网络上的相关内容,对于linux源码中已经存在的驱动文件,网络驱动内容只需要修改一下几点:网卡基地址,中断号,网卡工作模式,中断触发方式.
2.DM9000的修改完全按照以上要点.首先需要了解uclinux源码的大体结构.在uclinux-dist目录下找到linux-2.6.x文件夹.该文件夹中存放是linux的内核源码,其中包括arch,driver目录.
arch---各种处理器相关内容
driver--设备驱动内容
3.找到bf533-ezkit的外设注册文件:arch/blackfin/mach-bf533/boards/ezkit.c.bf533-ezkit中默认的网卡为SMC91x,参考本文件中SMC91x的注册信息,添加DM9000的参考信息:
#if defined(CONFIG_DM9000) || defined(CONFIG_DM9000_MODULE)
static struct resource dm9000_resources[] = {
[0]={
.name = "dm9000-regs",
.start = 0x20320000,
.end = 0x20320000 + 16,
.flags = IORESOURCE_MEM,
},
[1]={
.start = IRQ_PF5,
.end = IRQ_PF5,
.flags = IORESOURCE_IRQ | IORESOURCE_IRQ_LOWLEVEL,
},
};
static struct dm9000_plat_data bf533_dm9000_platdata={
.flags = DM9000_PLATF_16BITONLY,
};
static struct platform_device dm9000_device = {
.name = "dm9000",
.id = -1,
.num_resources = ARRAY_SIZE(dm9000_resources),
.resource = dm9000_resources,
.dev = {
.platform_data = &bf533_dm9000_platdata,

}
};
#endif
注意:io_addr = 0x20320000 :这个地址需要参考SSK的LAN_DM9000说明文档,该文档说明了DM9000在系统中分配的地址.
IRQ_PF5: 中断号
IORESOURCE_IRQ_LOWLEVEL:中断触发方式(低电平)
在本文件开始处添加include <linux/dm9000.h>
将DM9000设备注册到系统platform_device中
(在static struct platform_device *ezkit_devices[] __initdata中添加dm9000设备)
static struct platform_device *ezkit_devices[] __initdata = {

#if defined(CONFIG_DM9000) || defined(CONFIG_DM9000_MODULE)
&dm9000_device,
#endif

};
注:红色部分为需要添加的内容
4.进入DM9000驱动文件夹:linux-2.6.x/drivers/net,修改dm9000.h添加 #define CONFIG_DM9000 1
5.修改dm9000.c.
首先修改中断触发方式:低电平触发 #define DM9000_IRQ_FLAGS (IRQF_SHARED | IRQF_TRIGGER_LOW)
其次,修改io_data地址,参考裸板上的dm9000驱动程序
io_data = io_addr + 0x10
将uclinux下dm9000.c中的相应语句进行了修改:(原语句为:db->io_data = (void __iomem *)(base + 4);)
db->io_data = (void __iomem *)(base + 0x10);
另外,为了保证数据的完整写入,在每一个writeb(w)添加延时语句asm("ssync;");(readb:汇编实现,其中添加了延时)
因为网卡工作模式是16位,故需要修改
static void dm9000_outblk_16bit(void __iomen *reg, void *data, int count)
{
writesw(reg, data, (count+1)>>1);
}

writesw是汇编实现的,添加延时语句不方便,需要将此函数改为使用c语言实现.该函数类似于内存拷贝,实现的是将count个data数据输出到reg端口.修改后的函数为:
static void dm9000_outblk_16bit(void __iomem *reg, void *data, int count)
{
int tmplen;
int i;
tmplen = (count + 1)/2;
for(i = 0; i < tmplen; i++)
{
writew(((u16 *)data)[i], reg);
asm("ssync;");
}
}
需要特别注意的地方:
ezkit.c中dm9000_device结构体中name名称必须与dm9000.c中dm9000_driver结构体中的name名称一致,否则设备注册不到系统中,网络功能不可用,使用ping命令时出现"Network is unreachable"信息.


上传的附件
   20123221124583.rar [ 21.93 KB ]


这家伙很懒,什么也没有留下!
等级:论坛版主 参考IP地址:*.*.*.*
2012/3/2 21:13:00
vim007(论坛新手)
vim007
头衔:社区公民
帮派:无帮无派
帖数:50
金钱:397
积分:53
注册时间:2013/9/3
1信息 | 留言 | Email | 主页 | 编辑 | 管理 | 离线
uclinux下dm9000  发送乱码怎么破?

这家伙很懒,什么也没有留下!
等级:论坛新手 参考IP地址:*.*.*.*
2014/3/31 17:04:56
尊贵身份标志
andy(论坛版主)
andy
头衔:社区公民
帮派:无帮无派
帖数:2287
金钱:11132
积分:2263
注册时间:2011/6/8
2信息 | 留言 | Email | 主页 | 编辑 | 管理 | 离线
时序没配好吧,检查你在发送数据时是否加了延时,不加延时数据会出错。

这家伙很懒,什么也没有留下!
等级:论坛版主 参考IP地址:*.*.*.*
2014/4/1 1:24:05
尊贵身份标志
OpenADSP(管理员)
OpenADSP
头衔:社区公民
帮派:无帮无派
帖数:5187
金钱:34761
积分:6369
注册时间:2011/6/7
3信息 | 留言 | Email | 主页 | 编辑 | 管理 | 离线
等级:管理员 参考IP地址:*.*.*.*
2014/6/7 21:00:03
Powered by OpenADSP Copyright © 2010 www.Openadsp.com. All rights reserved.154475 Call, 1 Queries, Processed in 0.011719 second(s),