lpc_sich.c源码解析

学习Linux源码要先从大方向去把握,掌握好代码的整体框架,设计思想以后再去探究细节上的东西。这样可以让整个学习事半功倍,有效的提升学习的效率。分析这个代码我们也采用这样的方式,先从大方向入手,了解了整个脉络了以后,再针对细枝末节一个个解析。

static struct pci_driver lpc_sich_driver = {
    .name       = "lpc_sich",
    .id_table   = lpc_sich_ids,
    .probe      = lpc_sich_probe,
    .remove     = lpc_sich_remove,
};

首先是驱动结构体,大体上所有驱动都需要这么一个结构体,module_pci_driver会将这个驱动注册进内核。
name就是这个驱动的名称,用一个字符串表示;id_table是使用到这个驱动的设备列表;
probe很重要,是匹配设备和驱动的关键,没有它设备无法正常工作起来; remove则是在删除驱动时用的上的东西。

// id_table代码
static DEFINE_PCI_DEVICE_TABLE(lpc_sich_ids) = {
          // PCI_VENDOR_ID_JN  厂商号
        // PCI_DEVICE_ID_SICH_LPC 设备ID,本文件是配置的lpc驱动
    { PCI_DEVICE(PCI_VENDOR_ID_JN, PCI_DEVICE_ID_SICH_LPC) },
    { 0, }
};

接着解析lpc_sich_probe,即probe函数。 probe函数在设备驱动注册最后收尾工作,当设备的device 和其对应的driver 在总线上完成配对之后,系统就调用函数以及其他相关工作。
文件作者在这里使用了一个自定义的结构体

struct lpc_sich_adapter {
    void __iomem    *hst_regs;      //  驱动的基地址
    struct device   *dev;              // 设备信息
    int irq;                                  // 驱动
    struct irq_chip_generic *gc;  //  中断片信息
    unsigned features;                //  使用到的技术
};

注册过程开始前首先就为结构体分配内存
lpc_adapter = kzalloc(sizeof(*lpc_adapter), GFP_KERNEL);
lpc_sich_adapter内存分配成功后,调用pci_enable_device(pdev)使能设备。
调用pci_request_selected_regions(pdev, 1, KBUILD_MODNAME)为设备申请内存.

// 为lpc_adaper变量赋值
lpc_adapter->dev = &pdev->dev;  
    lpc_adapter->hst_regs = pci_iomap(pdev, LPC_HST_BAR, 0);  // hst是High-Speed Transfer
    lpc_adapter->features = 0;
// 设置主设备
pci_set_master(pdev);
// todo
set_bit(LPC_USE_MSI, &lpc_adapter->features);  
ret = pci_enable_msi(pdev);

irq_chip_generic结构体是用来描述驱动中断的结构体,该结构体需要进行很多设置,最主要的是ct属性,也就是chip_type。

c = irq_alloc_generic_chip("LPC_SICH", num_ct, irq_base, 
            lpc_adapter->hst_regs,
            handle_level_irq);

    ct = gc->chip_types;
    ct->regs.mask = LPC_IRQ_MASK;
    ct->regs.ack = LPC_IRQ;
    ct->chip.irq_mask = irq_gc_mask_set_bit;
    ct->chip.irq_unmask = irq_gc_mask_clr_bit;
    ct->chip.irq_ack = irq_gc_ack_set_bit;
    irq_setup_generic_chip(gc, IRQ_MSK(LPC_NR_IRQS), 0, 0, IRQ_NOPROBE | IRQ_LEVEL);

后续会调用一些函数对细节上进行一些设置,irq_set_handler_data用来设置中断,
lpc_enable自定义函数,通过修改寄存器的方式使能设备
lpc_mem_flash_init/lpc_fw_flash_init 这两个函数初始化内存资源,因为是通过pci进行连接的,所以直接走的总线。

irq_set_handler_data(lpc_adapter->irq, lpc_adapter);
    irq_set_chained_handler(lpc_adapter->irq, (irq_flow_handler_t) lpc_irq_handler_mfd);

    pci_read_config_word(pdev, PCI_COMMAND, &pci_command);
    pci_command |= PCI_COMMAND_IO; 
    pci_write_config_word(pdev, PCI_COMMAND, pci_command);

    pci_read_config_word(pdev, PCI_COMMAND, &pci_command);
    dev_info(&pdev->dev, "pci command = %#x\n", pci_command);

    lpc_enable(lpc_adapter);

    lpc_mem_flash_init(pdev,lpc_adapter);
    lpc_fw_flash_init(pdev,lpc_adapter);

下面这段话需要注意下,因为lpc也属于mfd设备(mutilfunction device), 因此需要调用mfd_add_devices

            lpc_sich_cells, ARRAY_SIZE(lpc_sich_cells), NULL,
            0, NULL);

后续再使能设备中断, 将pdev写入适配器,就基本上完成了probe函数

lpc_enable_irqs(lpc_adapter);

    pci_set_drvdata(pdev, lpc_adapter);

一路分析下来, 实际上整个文件都是在围绕着probe这个点做文章,在probe中需要对各个结构体做大量设置,以及调用若干函数,使得设备和驱动在总线上做匹配, 这些都需再以后做大量的积累。只有多去学习,理解,多去写,才能做到看到驱动也不发慌。

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 203,937评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,503评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,712评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,668评论 1 276
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,677评论 5 366
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,601评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,975评论 3 396
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,637评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,881评论 1 298
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,621评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,710评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,387评论 4 319
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,971评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,947评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,189评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 44,805评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,449评论 2 342

推荐阅读更多精彩内容