सवाल संदेश जोड़ने के लिए जो dmesg के साथ पढ़ा जाएगा?


मैं अपने dmesg आउटपुट में कुछ कस्टम संदेश लिखने की कोशिश कर रहा हूं। मैंने कोशिश की:

logger "Hello"

लेकिन यह काम नहीं करता है। यह बिना किसी त्रुटि के बाहर निकलता है, लेकिन आउटपुट में कोई "हैलो" प्रकट नहीं होता है:

dmesg

मैं फेडोरा 9 का उपयोग कर रहा हूं, और ऐसा लगता है कि कोई syslogd / klogd डिमन चल रहा है। हालांकि, मेरे सभी कर्नेल संदेश सफलतापूर्वक dmesg बफर में लिखे गए हैं।

कोई उपाय?


41
2018-05-10 18:24


मूल




जवाब:


dmesg कर्नेल बफर में क्या है, प्रदर्शित करता है logger के लिए है syslogd। मुझे लगता है कि अगर आप कर्नेल बफर में चीजों को प्रिंट करना चाहते हैं तो आपको एक ड्राइवर बनाने की आवश्यकता होगी जो इसका उपयोग करता है printk() कर्नेल समारोह। यदि आप बस इसे चाहते हैं /var/log/messages, फिर एक "सामान्य" सेटअप के साथ मुझे लगता है कि आपने क्या किया है logger पहले से ही ठीक है

ड्राइवर के साथ सबसे बुनियादी उदाहरण printk() होने वाला:

नमस्ते सी:

#include <linux/module.h>
#include <linux/kernel.h>

int init_module(void)
{
    printk(KERN_INFO "Hello world\n");
    return 0;
}

void cleanup_module(void)
{
    printk(KERN_INFO "Goodbye world\n");

}

makefile:

obj-m += hello.o

all:
    make -C /lib/modules/$(shell uname -r)/build M=$(PWD) modules

फिर:

$ make
$ sudo insmod hello.ko
$ dmesg | tail -n1
 [7089996.746366] Hello world

http://tldp.org/LDP/lkmpg/2.6/html/lkmpg.html#AEN121 अधिक जानकारी के लिए...


34
2018-05-10 18:30



मुझे एक त्रुटि मिली, क्योंकि आपने पहले रिक्त स्थान लगाए हैं make -C ... एक टैब के बजाय मेकफ़ाइल में, इसलिए मेकफ़ाइल की उपरोक्त सामग्री की प्रतिलिपि काम नहीं करती - अधिक यहाँ। मैं इसे एक संपादन में जोड़ने में असमर्थ हूं ... वैसे धन्यवाद, महान जवाब। - Wilf


आप रूट के रूप में लिख सकते हैं /dev/kmsg कर्नेल संदेश बफर पर प्रिंट करने के लिए:

 fixnum:~# echo Some message > /dev/kmsg
 fixnum:~# dmesg | tail -n1
 [28078118.692242] Some message

मैंने इसे अपने सर्वर और एक एम्बेडेड लिनक्स डिवाइस पर परीक्षण किया है, और यह दोनों पर काम करता है, इसलिए मुझे लगता है कि यह हर जगह काफी काम करता है।


101
2018-02-23 14:47



दिलचस्प है कि उबंटू में, यह रूट के रूप में काम करता है लेकिन सूडो के साथ नहीं। एक वास्तव में जड़ बनने की जरूरत है। - dotancohen
असल में, ऐसा इसलिए है क्योंकि इनपुट रीडायरेक्शन आपके खोल से संभाला जाता है, जो उच्च अधिकारों के साथ नहीं चल रहा है। दौड़ने का प्रयास करें echo Some message | sudo tee /dev/kmesg गैर रूट के रूप में। - wvdschel
यह काम करता है। धन्यवाद, दिलचस्प। वैसे, इसकी kmsg नहीं kmesg लेकिन मैं भी उलझन में हूँ dmesg ई है! - dotancohen
कर्नेल मॉड्यूल संकलित करने से बहुत आसान है - e271p314


काइल के मॉड्यूल के आधार पर:


#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/proc_fs.h>
#include <asm/uaccess.h>

static int pk_write(struct file *file, const char *buffer, unsigned long count, void *data)
{
        char string[256];
        count = count < 255 ? count : 255;

        if(copy_from_user(string, buffer, count))
                return -EFAULT;

        string[count] = '\0';        
        printk(string);
        return count;
}


static int __init printk_init(void)
{
        struct proc_dir_entry *pk_file;

        pk_file = create_proc_entry("printk", 0222, NULL);
        if(pk_file == NULL)
                return -ENOMEM;

        pk_file->write_proc = pk_write;
        pk_file->owner = THIS_MODULE;

        return 0;
}

static void __exit printk_cleanup(void)
{
        remove_proc_entry("printk", NULL);
}

module_init(printk_init);
module_exit(printk_cleanup);
MODULE_LICENSE("GPL");

उपयोगकर्ता स्थान से एक प्रिंटक करने के लिए:

echo "Hello" > /proc/printk

13
2018-05-11 09:34



यह केवल लिनक्स कर्नेल <3.10 के लिए काम करता है। एक नए विकल्प के लिए मेरा जवाब देखें। - kevinf


@ Calandoa का जवाब अब कर्नेल +3.10 के लिए काम नहीं करता है। उसका कोड संयुक्त, और उदाहरण कोड मिला यहाँ। फिर कोड गुणवत्ता पर सुधार हुआ ...

कोड printk_user.c में सहेजा गया

#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/proc_fs.h>
#include <asm/uaccess.h>

static ssize_t write_proc(struct file *filep, const char *buffer, size_t count, loff_t *offsetp)
{
    char string[256];
    count = count < 255 ? count : 255;

    if(copy_from_user(string, buffer, count) != 0) {
        return -EFAULT;
    }

    string[count] = '\0';
    printk(string);
    return count;
}

static const struct file_operations proc_fops = {
    .owner = THIS_MODULE,
    .write = write_proc,
};

static int proc_init(void) {
    struct proc_dir_entry *proc_file;
    proc_file = proc_create("printk_user", 0, NULL, &proc_fops);

    if(proc_file == NULL) {
        return -ENOMEM;
    }

    return 0;
}

static void proc_cleanup(void) {
    remove_proc_entry("printk_user", NULL);
}

MODULE_LICENSE("GPL"); 
module_init(proc_init);
module_exit(proc_cleanup);

इस मेकफ़ाइल का उपयोग करें

TARGET = printk_user
obj-m := $(TARGET).o

KERNEL_VERSION=$(shell uname -r)
KDIR = /lib/modules/$(KERNEL_VERSION)/build
PWD = $(shell pwd)

printk:
    $(MAKE) -C $(KDIR) M=$(PWD) modules

clean:
    $(MAKE) -C $(KDIR) M=$(PWD) clean

5
2017-11-25 20:59





काइल के जवाब के आधार पर, यहाँ एक त्वरित ट्यूटोरियल दिखा रहा है कि यह कैसे करना है।


3
2018-05-10 18:35