首页 | 博客群 | 公社 | 专栏 | 论坛 | 图片 | 资讯 | 注册 | 帮助 | 博客联播 | 随机访问
指纹- -| 回首页 | 2006年索引 | - -今天,我天始新的生活

CS8900A驱动在linux-2.6.16上的变化

关键词CS8900A    smdk2410    2.6.16    linux                                          

CS8900A在linux-2.6.16上的移植

  关于cs8900a在smdk2410平台,内核2.6.X上的移植网上已有不少转载,这里我简单分析
一下2.6.16内核上的移植。

    解决出现如下的问题:

    “MM: invalid domain in supersection mapping for 0x18000000000 at 0xe0000000

  
  基本步骤(引用):

 (1) #cp cs8900.c  ./drivers/net/arm/
        #cp cs8900.h  ./drivers/net/arm/
   
  并在cs8900_probe()函数中,memset (&priv,0,sizeof (cs8900_t));函数之后添加如下
两条语句:

 __raw_writel(0x2211d110,S3C2410_BWSCON);
 __raw_writel(0x1f7c,S3C2410_BANKCON3);
 
注:事实上我并没有加这两行,2.6.16?u-boot-1.1.4已经处理好相应时序了。比如设置bank3
的是上面BWSCON中的“d1”,bankcon3是0x1f4c,与0x1f7c的差别就是:

 Tcah [5:4] Address hold time after nGCSn-----片选pin
  
 00 = 0 clock ---->0 01 = 1 clock
 10 = 2 clocks       11 = 4 clocks----->3
 
 7-4=3
 
 应该跟电气性能相关
 。

(2)修改drivers/net/arm/目录下的Kconfig文件,在最后添加如下内容:
Config ARM_CS8900
   tristate "CS8900 support"
   depends on NET_ETHERNET && ARM && ARCH_SMDK2410
 help
   Support for CS8900A chipset based Ethernet cards. If you have a network
   (Ethernet) card of this type, say Y and read the  Ethernet-HOWTO, available
   from  as well as .
   To compile this driver as a module, choose M here and read
.  The module will be
   called cs8900.o.
  
注:内核系统配置文件由2.4版本的config.in变成了2.6版本Kconfig文件,在这个文件里
面添加如上内容,则在运行make menuconfig或者make xconfig命令的时候就会出现:
        [ ]   CS8900 support 
这一选项。

(3)修改drivers/net/arm/目录下的Makefile文件,在最后添加如下内容:

      obj-$(CONFIG_ARM_CS8900)    += cs8900.o
     
注:2.6版本内核的Makefile文件也与2.4版本的有所不同。添加以上语句,就会使内核在编
译的时候根据配置将cs8900A的驱动程序以模块或静态的方式编译到内核当中。

(4)在/arch/arm/mach-s3c2410/mach-smdk2410.c文件中,找到smdk2410_iodesc[]结构
数组,添加如下如下内容:

{vSMDK2410_ETH_IO, 0x19000000, SZ_1M, MT_DEVICE}

修改之后变成了:

 static struct map_desc smdk2410_iodesc[] __initdata = {
       /* nothing here yet */
        /* Map the ethernet controller CS8900A */       
        {vSMDK2410_ETH_IO, 0x19000000, SZ_1M, MT_DEVICE}
};

 注:由于在驱动程序的开发的时候,在驱动程序当中所用到的跟设备有关的地址都是虚拟地址,
 也就是说驱动程序操作的都是虚拟地址,那么要使驱动程序对设备的操作反映到设备上去,就
 得将设备的物理地址映射到正确的虚拟地址上去,从而保证驱动程序对虚拟地址的操作也就是
 对相应的物理地址操作。以上添加的语句就是为了将网卡的物理地址(0x19000000)映射到
 vSMDK2410_ETH_IO所指向的虚拟地址上去,上面的结构还定义了网卡虚拟地址所占用的区间,
 也就是从vSMDK2410_ETH_IO开始的SZ_1M大小的去间,并指定了该区间所指向的域(的属性)。
 (疑问:在本开发板上,网卡占用的是CPU的nGCS3片选信号,也就是在Bank3,根据处理器的地
 址空间定义,这个地址应该是0x18000000,为什么这里使用的是0x19000000?查找到2.4.18的内
 核当中,也是用0x19000000来进行映射。)
 
 

这里讨论下下 map_desc


struct map_desc {------------------------------2.6.16
          unsigned long virtual;---------------虚地址
          unsigned long pfn;-------------------Page Frame Number 页帧号
          unsigned long length;
          unsigned int type;
  };
 
struct map_desc {------------------------------2.6.9
 13         unsigned long virtual;
 14         unsigned long physical;------------物理地址
 15         unsigned long length;
 16         unsigned int type;
 17 };
 

pfn / physical 这两者是什么关系呢?

先看调用它们的函数


  void __init create_mapping(struct map_desc *md)-------------2.6.16
 {
         unsigned long virt, length;
         int prot_sect, prot_l1, domain;
         pgprot_t prot_pte;
         unsigned long off = (u32)__pfn_to_phys(md->pfn);
 
         if (md->virtual != vectors_base() && md->virtual < TASK_SIZE) {
                 printk(KERN_WARNING "BUG: not creating mapping for "
                        "0x%08llx at 0x%08lx in user region\n",
                        __pfn_to_phys((u64)md->pfn), md->virtual);
                return;
         }
 
        if ((md->type == MT_DEVICE || md->type == MT_ROM) &&
             md->virtual >= PAGE_OFFSET && md->virtual < VMALLOC_END) {
                 printk(KERN_WARNING "BUG: mapping for 0x%08llx at 0x%08lx "
                        "overlaps vmalloc space\n",
                        __pfn_to_phys((u64)md->pfn), md->virtual);
         }
 
         domain    = mem_types[md->type].domain;
         prot_pte  = __pgprot(mem_types[md->type].prot_pte);
         prot_l1   = mem_types[md->type].prot_l1 | PMD_DOMAIN(domain);
         prot_sect = mem_types[md->type].prot_sect | PMD_DOMAIN(domain);
 
         /*
          * Catch 36-bit addresses
          */
         if(md->pfn >= 0x100000) {
                 if(domain) {
                         printk(KERN_ERR "MM: invalid domain in supersection "
                                 "mapping for 0x%08llx at 0x%08lx\n",
                                __pfn_to_phys((u64)md->pfn), md->virtual);
                        return;
                 }
                 if((md->virtual | md->length | __pfn_to_phys(md->pfn))

/*这里copy一些定义作为注释
Convert a physical address to a Page Frame Number and back
*/
//#define __phys_to_pfn(paddr)    ((paddr) >> PAGE_SHIFT)
//#define __pfn_to_phys(pfn)      ((pfn) << PAGE_SHIFT)
 
//#ifndef _ASMARM_PAGE_H
//#define _ASMARM_PAGE_H
 
//#include
 
 /* PAGE_SHIFT determines the page size */
//#define PAGE_SHIFT             
12

问题就在这儿了,两者是移12位的关系
 
                         & ~SUPERSECTION_MASK) {
                         printk(KERN_ERR "MM: cannot create mapping for "
                                 "0x%08llx at 0x%08lx invalid alignment\n",
                                __pfn_to_phys((u64)md->pfn), md->virtual);
                        return;
                 }
 
                 /*
                  * Shift bits [35:32] of address into bits [23:20] of PMD
                  * (See ARMv6 spec).
                  */
                 off |= (((md->pfn >> (32 - PAGE_SHIFT)) & 0xF) << 20);
         }

        virt   = md->virtual;
         off   -= virt;
         length = md->length;

     ...........
     ...........
     ...........
   
 }
 
 
结论:
 
关于linux-2.6.16的头文件就应该改成
 
#ifndef _INCLUDE_SMDK2410_H_
#define _INCLUDE_SMDK2410_H_
#include
#define pSMDK2410_ETH_IO 
__phys_to_pfn(0x19000000)
#define vSMDK2410_ETH_IO  0xE0000000
#define SMDK2410_ETH_IRQ   IRQ_EINT9
#endif // _INCLUDE_SMDK2410_H_

【作者: solomoon】【访问统计:】【2006年04月20日 星期四 16:30】【注册】【打印

搜索

Google

Trackback

你可以使用这个链接引用该篇文章 http://publishblog.blogchina.com/blog/tb.b?diaryID=4914641

博客手拉手

回复

- 评论人:zycfrank   2007-05-17 17:22:46   

你好,我现在在做2.6.14内核上的CS8900移植,就是找不到可以用的CS8900源文件,希望你给我一份
zycfrank@163.com

- 评论人:songh717   2007-03-18 20:02:34   

大侠你好,我在linux-12.6.15上按照你的办法进行8900的移植,并且#define pSMDK2410_ETH_IO __phys_to_pfn(0x19000000)
但是却出现这样的问题
Code: e283200a e3520201 e1a00002 328004f2 (e1c060b0)
〈0〉Kernel panic - not syncing: Attempted to kill init!

- 评论人:hiboy   2007-02-08 17:26:40   

求cs8900.c 和cs8900.h文件。谢谢
shnicebin@gmail.com

- 评论人:weibing   2007-02-06 12:00:22   

十分感谢,困扰我一整天的问题终于解决。添加
#define pSMDK2410_ETH_IO __phys_to_pfn(0x19000000)
这一句后我的cs89x0.c终于在Linux-2.6.19.2跑起来。
再次感谢 ^_^

- 评论人:weibing   2007-02-06 12:00:05   

十分感谢,困扰我一整天的问题终于解决。添加
#define pSMDK2410_ETH_IO __phys_to_pfn(0x19000000)
这一句后我的cs89x0.c终于在Linux-2.6.19.2跑起来。
再次感谢...

- 评论人:烂人   2007-01-11 19:15:48   

牛人阿.
8900.c 8900.h的文件在下面的网页里有.可以用.
http://www.linuxforum.net/forum/showflat.php?Cat=&Board=embedded&Number=546995&page=0&view=collapsed&sb=5&o=all&fpart=4&vc=1

- 评论人:烂人   2007-01-11 19:15:44   

牛人阿.
8900.c 8900.h的文件在下面的网页里有.可以用.
http://www.linuxforum.net/forum/showflat.php?Cat=&Board=embedded&Number=546995&page=0&view=collapsed&sb=5&o=all&fpart=4&vc=1

- 评论人:zw   2006-12-24 16:17:55   

谢谢,能给我一份源代码吗?zw69212@163.com

- 评论人:fanni   2006-12-06 20:02:13   

您好大侠 恳请您发2.6下的8900.C及8900.h这两个文件给我 非常感谢!Emil:qianfan726@126.com

- 评论人:fanni   2006-12-06 20:00:49   

您好大侠 恳请您发2.6下的8900.C及8900.h这两个文件给我 非常感谢!

- 评论人:anonymous   2006-10-19 11:07:02   

我也找不到8900的驱动,给我一份吧,谢谢2008

- 评论人:anonymous   2006-09-20 15:53:38   

您好,我现在正在做8900在26上的移植,但怎么找都找不到8900和8900两个文件,您能发一份到我邮箱吗,万分感谢

验证码:   
评论内容: