реклама на сайте
подробности

 
 
> Petalinux. Kernel module.
doom13
сообщение Apr 6 2016, 20:23
Сообщение #1


Профессионал
*****

Группа: Свой
Сообщений: 1 404
Регистрация: 11-03-11
Из: Минск, Беларусь
Пользователь №: 63 539



Приветствую.
Пытаюсь сделать модуль ядра для управления AXI GPIO. По мануалу сгенерил шаблон модуля и вношу в него свои изменения. Отлаживаю работу модуля в QEMU. При загрузке модуля (insmod) выполняется функция инициализации (printk в консоль выводит сообщение) в ней происходит вызов platform_driver_register(&axi_gpio_platform_driver), которая должна "пнуть" вызов axi_gpio_probe(), но вызов axi_gpio_probe() почему-то не происходит (сообщение printk в консоль о выполнении axi_gpio_probe() не выводятся). При этом platform_driver_register(&axi_gpio_platform_driver) возвращает 0.
В чём может быть проблема?

Спасибо.
Go to the top of the page
 
+Quote Post
 
Start new topic
Ответов
nill
сообщение Apr 8 2016, 06:53
Сообщение #2


Частый гость
**

Группа: Validating
Сообщений: 124
Регистрация: 10-08-05
Пользователь №: 7 502



Цитата(doom13 @ Apr 7 2016, 14:58) *
Этого достаточно?

Device tree передаётся qemu параметром -dtb и этот параметр есть в строке запуска, так что должно быть достаточно. Другое дело - проследить, чтоб передавался нужный файл. А вообще, содержимое device tree можно посмотреть в /proc/device-tree. Вы добавили своё устройство в device tree? Я думаю, что проблема именно в этом месте.

Для загрузки платформенного драйвера, который Вы решили сделать, необходимо выполнить несколько условий:
1. Добавить устройство в device tree. Ключевым параметром здесь является compatible = "name" и именно по имени name ядро решает, какой драйвер соответствует данному устройству.
2. Заполнить структуру of_device_id и указать в ней имя драйвера. Оно должно соответствовать name в device tree.
3. Заполнить струкруру platform_driver и в её поле driver.of_match_table указать Вашу of_device_id.
4. Передать структуру platform_driver макросу module_platform_driver().
Если всё сделать правильно, то ядро само вызовет функцию probe() после загрузки драйвера.

Покажите код Вашего драйвера (если он не слишком длинный).
Go to the top of the page
 
+Quote Post
doom13
сообщение Apr 8 2016, 07:39
Сообщение #3


Профессионал
*****

Группа: Свой
Сообщений: 1 404
Регистрация: 11-03-11
Из: Минск, Беларусь
Пользователь №: 63 539



Цитата(nill @ Apr 8 2016, 09:53) *
Покажите код Вашего драйвера (если он не слишком длинный).

Там просто стандартный шаблон, который сгенерировала команда petalinux-create -t modules --name axi_gpio0 --enable:
CODE

/* axi_gpio0.c - The simplest kernel module.
*/
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/module.h>
#include <linux/slab.h>
#include <linux/io.h>
#include <linux/interrupt.h>

#include <linux/of_address.h>
#include <linux/of_device.h>
#include <linux/of_platform.h>

/* Standard module information, edit as appropriate */
MODULE_LICENSE("GPL");
MODULE_AUTHOR ("Xilinx corp.");
MODULE_DESCRIPTION ("axi_gpio0 - loadable module for axi_gpio control");

#define DRIVER_NAME "axi_gpio0"


int test_value = 0;


struct axi_gpio0_local {
int irq;
unsigned long mem_start;
unsigned long mem_end;
void __iomem *base_addr;
};

static irqreturn_t axi_gpio0_irq(int irq, void *lp)
{
printk("axi_gpio0 interrupt\n");
return IRQ_HANDLED;
}

static int axi_gpio0_probe(struct platform_device *pdev)
{
struct resource *r_irq; /* Interrupt resources */
struct resource *r_mem; /* IO mem resources */
struct device *dev = &pdev->dev;
struct axi_gpio0_local *lp = NULL;

int rc = 0;
int counter = 0;

test_value = 111;

printk("<1>Hello module world.\n");
printk(KERN_ERR "In probe() function\n");

dev_info(dev, "Device Tree Probing\n");

test_value = 222;

/*
// Get iospace for the device
r_mem = platform_get_resource(pdev, IORESOURCE_MEM, 0);
if (!r_mem) {
dev_err(dev, "invalid address\n");
return -ENODEV;
}

lp = (struct axi_gpio0_local *) kmalloc(sizeof(struct axi_gpio0_local), GFP_KERNEL);
if (!lp) {
dev_err(dev, "Cound not allocate axi_gpio0 device\n");
return -ENOMEM;
}

dev_set_drvdata(dev, lp);

lp->mem_start = r_mem->start;
lp->mem_end = r_mem->end;

printk("lp->mem_start = %x\n", lp->mem_start);
printk("lp->mem_end = %x\n", lp->mem_end);

if (!request_mem_region(lp->mem_start,
lp->mem_end - lp->mem_start + 1,
DRIVER_NAME)) {
dev_err(dev, "Couldn't lock memory region at %p\n",
(void *)lp->mem_start);
rc = -EBUSY;
goto error1;
}

lp->base_addr = ioremap(lp->mem_start, lp->mem_end - lp->mem_start + 1);
if (!lp->base_addr) {
dev_err(dev, "axi_gpio0: Could not allocate iomem\n");
rc = -EIO;
goto error2;
}

// Get IRQ for the device
r_irq = platform_get_resource(pdev, IORESOURCE_IRQ, 0);
if (!r_irq) {
dev_info(dev, "no IRQ found\n");
dev_info(dev, "axi_gpio0 at 0x%08x mapped to 0x%08x\n",
(unsigned int __force)lp->mem_start,
(unsigned int __force)lp->base_addr);
return 0;
}
lp->irq = r_irq->start;

rc = request_irq(lp->irq, &axi_gpio0_irq, 0, DRIVER_NAME, lp);
if (rc) {
dev_err(dev, "testmodule: Could not allocate interrupt %d.\n",
lp->irq);
goto error3;
}

dev_info(dev,"axi_gpio0 at 0x%08x mapped to 0x%08x, irq=%d\n",
(unsigned int __force)lp->mem_start,
(unsigned int __force)lp->base_addr,
lp->irq);

return 0;
error3:
free_irq(lp->irq, lp);
error2:
release_mem_region(lp->mem_start, lp->mem_end - lp->mem_start + 1);
error1:
kfree(lp);
dev_set_drvdata(dev, NULL);
*/
return rc;
}

static int axi_gpio0_remove(struct platform_device *pdev)
{
struct device *dev = &pdev->dev;
struct axi_gpio0_local *lp = dev_get_drvdata(dev);
free_irq(lp->irq, lp);
release_mem_region(lp->mem_start, lp->mem_end - lp->mem_start + 1);
kfree(lp);
dev_set_drvdata(dev, NULL);

test_value = 333;

return 0;
}

//#ifdef CONFIG_OF
static struct of_device_id axi_gpio0_of_match[] = {
{ .compatible = "vendor,axi_gpio0", },
{ /* end of list */ },
};
MODULE_DEVICE_TABLE(of, axi_gpio0_of_match);
//#else
//# define axi_gpio0_of_match
//#endif


static struct platform_driver axi_gpio0_driver = {
.driver = {
.name = DRIVER_NAME,
.owner = THIS_MODULE,
.of_match_table = axi_gpio0_of_match,
},
.probe = axi_gpio0_probe,
.remove = axi_gpio0_remove,
};


static int __init axi_gpio0_init(void)
{
int result = 12;

printk(KERN_INFO "Hello module world.\n");
printk(KERN_INFO "Hello module world.\n");
printk(KERN_INFO "In init() function 10:14.\n");
//dev_info(dev, "<1>Hello module world.\n");
//printk("<1>Module parameters were (0x%08x) and \"%s\"\n", myint,
// mystr);

printk(KERN_INFO "result = %d\n", result);
//test_counter();

printk(KERN_ERR "axi_gpio0_driver.probe = %p\n", axi_gpio0_driver.probe);
printk(KERN_ERR "axi_gpio0_probe = %p\n", axi_gpio0_probe);

result = platform_driver_register(&axi_gpio0_driver);
printk(KERN_INFO "result = %d\n", result);
printk(KERN_INFO "test_value = %d\n", test_value);


return result;
}


static void __exit axi_gpio0_exit(void)
{
platform_driver_unregister(&axi_gpio0_driver);
printk(KERN_INFO "Goodbye module world.\n");
printk(KERN_INFO "test_value = %d\n", test_value);
}

module_init(axi_gpio0_init);
module_exit(axi_gpio0_exit);

, в теле axi_gpio0_probe() только printk, хочу увидеть что оно в неё заходит.

Цитата(nill @ Apr 8 2016, 10:36) *
Вам же говорят, что это каталог rolleyes.gif Зайдите внутрь, там всё дерево разложено по каталогам и файлам.

Ссори, не то закопипастил в посте выше, исправил, не даёт зайти в каталог, переходит сразу в каталог /sys/firmware/devicetree/base (или так и надо?).
Go to the top of the page
 
+Quote Post

Сообщений в этой теме
- doom13   Petalinux. Kernel module.   Apr 6 2016, 20:23
- - nill   platform_driver_register() всего лишь регистрирует...   Apr 7 2016, 08:07
|- - doom13   Цитата(nill @ Apr 7 2016, 11:07) platform...   Apr 7 2016, 08:58
- - doom13   Уточню. Нашёл исходный код platform_driver_registe...   Apr 7 2016, 10:35
|- - doom13   Цитата(nill @ Apr 8 2016, 09:53) А вообще...   Apr 8 2016, 07:31
- - nill   Вам же говорят, что это каталог Зайдите внутрь, ...   Apr 8 2016, 07:36
- - nill   axi_gpio0_init(void) и axi_gpio0_exit(void) можно ...   Apr 8 2016, 07:57
|- - doom13   Цитата(nill @ Apr 8 2016, 10:57) axi_gpio...   Apr 8 2016, 08:06
|- - doom13   Цитата(nill @ Apr 8 2016, 11:08) Это имя ...   Apr 8 2016, 08:19
- - nill   Это имя дожно быть одинаковым в драйвере и device ...   Apr 8 2016, 08:08
- - nill   ^ Да, это оно. Так, кажется я начал о чём-то догад...   Apr 8 2016, 08:20
|- - doom13   Цитата(nill @ Apr 8 2016, 11:20) Так, каж...   Apr 8 2016, 08:28
- - nill   axi_gpio_0 определён в карте памяти, посмотрите в ...   Apr 8 2016, 08:41
|- - doom13   Цитата(nill @ Apr 8 2016, 11:41) axi_gpio...   Apr 8 2016, 09:30
- - nill   В файле pl.dtsi есть секция axi_gpio_0: gpio@10003...   Apr 9 2016, 06:02
|- - doom13   Цитата(nill @ Apr 9 2016, 09:02) В файле ...   Apr 9 2016, 08:10
- - nill   Других идей у меня, к сожалению, нет. Возможно, чт...   Apr 10 2016, 06:58
- - doom13   RE: Petalinux. Kernel module.   Apr 11 2016, 07:31
|- - nill   Цитата(doom13 @ Apr 11 2016, 14:31) Кодro...   Apr 12 2016, 08:02
- - doom13   nill, cпасибо. Попробую поэкспериментировать с жел...   Apr 12 2016, 09:20


Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 26th July 2025 - 14:52
Рейтинг@Mail.ru


Страница сгенерированна за 0.01396 секунд с 7
ELECTRONIX ©2004-2016