Управление памятью в ядре C - Linux - PullRequest
0 голосов
/ 29 февраля 2020

Я пытаюсь написать Linux Модуль ядра, я наткнулся на действительно простую проблему.

У меня есть указатель на структуру, предоставленную ядром, я просто хотел бы скопировать один из элементы локальной переменной.

При запуске моего кода данные, присвоенные vairable, возвращаются как (null).

Я прочитал много сообщений, касающихся управления памятью, но все еще отсутствует что-то.

#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/usb.h>
#include <linux/usb/hcd.h>
#include <linux/list.h>
#include <linux/slab.h>

MODULE_LICENSE("GPL");

struct usb_bus *bus;  
size_t ret;

static char *get_usb_bus_serial(struct usb_bus *bus)
{
    char *serial;
    serial = kmalloc(sizeof(char) * 128, GFP_KERNEL);
    strcpy(serial, bus->root_hub->serial);
    return serial;
}

static int __init usb_fun_init (void)  
{  
    int id;
    int chix;
    struct usb_device *dev, *childdev = NULL;

    printk(KERN_INFO "\n************************************ in init\n"); 
    mutex_lock(&usb_bus_idr_lock);

    idr_for_each_entry(&usb_bus_idr, bus, id)
    {  
        printk(KERN_INFO "***************** Begins ****************");  

        printk(KERN_INFO "Vendor ID = %x", bus->root_hub->descriptor.idVendor);  
        printk(KERN_INFO "Product ID = %x", bus->root_hub->descriptor.idProduct);  
        printk(KERN_INFO "Serial Number = %x", bus->root_hub->descriptor.iSerialNumber);  
        //printk(KERN_INFO "Manu = %s", bus->root_hub->descriptor.iManufacturer);  
        printk(KERN_INFO "Manu = %s", bus->root_hub->manufacturer);  
        printk(KERN_INFO "Product = %s", bus->root_hub->product);  
        printk(KERN_INFO "Serial Number = %s", bus->root_hub->serial); 
        printk(KERN_INFO "Serial Number = %s", get_usb_bus_serial(bus));
        //printk(KERN_INFO "\nManufacturer = %s", udev.bus.iManufacturer);   - error: request for member ‘iManufacturer’ in something not a structure or union      


        dev = bus->root_hub;
        usb_hub_for_each_child(dev, chix, childdev)
        {
            if(childdev)
            {

                printk(KERN_INFO "***************** Child device ****************"); 

                usb_lock_device(childdev);
                printk(KERN_INFO "Vendor ID = %x", childdev->descriptor.idVendor);  
                printk(KERN_INFO "Product ID = %x", childdev->descriptor.idProduct);  
                printk(KERN_INFO "Serial Number = %x", childdev->descriptor.iSerialNumber);  
                printk(KERN_INFO "Manu = %s", childdev->manufacturer);  
                printk(KERN_INFO "Product = %s", childdev->product);  
                printk(KERN_INFO "Serial Number = %s", childdev->serial);  
                usb_unlock_device(childdev);
            }
        }
    }

    mutex_unlock(&usb_bus_idr_lock);    
    return 0;  
}

static void __exit usb_fun_exit (void)  
{  
    printk(KERN_INFO "\n************************************ in exit\n");  
} 

module_init(usb_fun_init);
module_exit(usb_fun_exit); 

Вывод

Feb 29 06:54:25 ubuntu kernel: [ 5238.163373] Serial Number = (null)

РЕДАКТИРОВАТЬ

После исправления проблем в комментариях при вставке модуля разыменование нулевого указателя происходит. Я все еще не понимаю, что именно я делаю, чтобы вызвать эту проблему.

1 Ответ

0 голосов
/ 29 февраля 2020

Как указывало @ ens c, следовало бы использовать kmallo c () вместо vmallo c (), приведенный выше код запускается и возвращает правильный вывод

Feb 29 07:31:31 ubuntu kernel: [  725.618665] Serial Number = 0000:02:00.0
...