Note that there are some explanatory texts on larger screens.

plurals
  1. POWrite timer in Linux device driver
    primarykey
    data
    text
    <p>I'm newbies with the module linux. I try to create a counter module where the counter is increment on timer callback. The result of the counter must be send to an other module (a memory module).</p> <pre><code>#include &lt;linux/init.h&gt; #include &lt;linux/module.h&gt; #include &lt;linux/kernel.h&gt; #include &lt;linux/slab.h&gt; #include &lt;linux/fs.h&gt; #include &lt;linux/errno.h&gt; #include &lt;linux/types.h&gt; #include &lt;linux/proc_fs.h&gt; #include &lt;linux/fcntl.h&gt; #include &lt;asm/system.h&gt; #include &lt;asm/uaccess.h&gt; MODULE_AUTHOR("Helene"); MODULE_DESCRIPTION("Module memory"); MODULE_SUPPORTED_DEVICE("none"); MODULE_LICENSE("Dual BSD/GPL"); /* Global variables of the driver */ /* Buffer to store data */ char *memory_buffer; int result; struct file_operations memory_fops; int memory_open(struct inode *inode, struct file *filp) { // printk(KERN_DEBUG "Opening memory module\n"); return 0; } int memory_release(struct inode *inode, struct file *filp) { // printk(KERN_DEBUG "Releasing of memory module\n"); return 0; } ssize_t memory_read(struct file *filp, char *buf, size_t count, loff_t *f_pos){ // printk(KERN_DEBUG "Reading memory module : %s\n", buf); if (*f_pos &gt; 0) return 0; if (count &gt; strlen(memory_buffer)) count = strlen(memory_buffer); copy_to_user(buf,memory_buffer,count); *f_pos = *f_pos + count; return count; } ssize_t memory_write( struct file *filp, const char *buf, size_t count, loff_t *f_pos) { // printk(KERN_DEBUG "Writing memory module : %s\n", buf); copy_from_user(memory_buffer, buf, count); return count; } static int __init memory_init(void) { /* Registering device */ result = register_chrdev(0, "memory", &amp;memory_fops); if (result &lt; 0) { printk(KERN_DEBUG "memory: cannot obtain major number \n"); return result; } /* Allocating memory for the buffer */ memory_buffer = kmalloc(1, GFP_KERNEL); if (!memory_buffer) { result = -ENOMEM; goto fail; } memset(memory_buffer, 0, 1); printk(KERN_ALERT "Inserting memory module : %d\n", result); return 0; fail: //memory_exit(); return result; } static void __exit memory_exit(void) { /* Freeing the major number */ unregister_chrdev(result, "memory"); /* Freeing buffer memory */ if (memory_buffer) { kfree(memory_buffer); } printk(KERN_DEBUG "Removing memory module\n"); } struct file_operations memory_fops = { owner: THIS_MODULE, read: memory_read, write: memory_write, open: memory_open, release: memory_release }; module_init(memory_init); module_exit(memory_exit); </code></pre> <p>The memory module works. My problem is when I call the function : filp_open/fp->f_op->write/filp_close on the function timer callback. I have test these functions out of the timer callback and it's work.</p> <p>Why the filp_open function (&amp; co) don't work on timer callback function ?</p> <pre><code>#include &lt;linux/init.h&gt; #include &lt;linux/module.h&gt; #include &lt;linux/kernel.h&gt; /* printk() */ #include &lt;linux/slab.h&gt; /* kmalloc() */ #include &lt;linux/fs.h&gt; /* everything... */ #include &lt;linux/errno.h&gt; /* error codes */ #include &lt;linux/types.h&gt; /* size_t */ #include &lt;linux/proc_fs.h&gt; #include &lt;linux/fcntl.h&gt; /* O_ACCMODE */ #include &lt;asm/system.h&gt; /* cli(), *_flags */ #include &lt;asm/uaccess.h&gt; /* copy_from/to_user */ MODULE_LICENSE("GPL"); static struct timer_list my_timer; int cptNbClic ; int result; struct file_operations timer_fops; int write_file_system(struct file *fp, char * buf){ int nb; mm_segment_t old_fs=get_fs(); set_fs(get_ds()); nb = fp-&gt;f_op-&gt;write(fp,buf ,10, &amp;fp-&gt;f_pos); set_fs(old_fs); return nb; } void writeInMemory(void){ // printk(KERN_DEBUG "busy %d\n", busy); int nbwrite; char buf[3]; int fmemory; fmemory=filp_open ("/dev/memory", O_WRONLY | O_APPEND | O_CREAT,0); //don't work on this function if (fmemory==NULL){//verification de l'ouverture printk(KERN_ALERT "filp_open error input memory!!.\n"); return -1; } sprintf(buf, "%d", cptNbClic); printk(KERN_DEBUG "%d\n", cptNbClic); nbwrite = write_file_system(fmemory, buf); filp_close(fmemory, 0); } void my_timer_callback( unsigned long data ) { cptNbClic++; printk(KERN_DEBUG "cptNbClic %d\n", cptNbClic); writeInMemory(); setup_timer(&amp;my_timer, my_timer_callback, 0); mod_timer(&amp;my_timer, jiffies + msecs_to_jiffies(1000)); } static int timer_open(struct inode *inode, struct file *filp) { /* setup your timer to call my_timer_callback */ cptNbClic = 0; setup_timer(&amp;my_timer, my_timer_callback, 0); /* setup timer interval to 200 msecs */ mod_timer(&amp;my_timer, jiffies + msecs_to_jiffies(1000)); return 0; } static int timer_release(struct inode *inode, struct file *filp) { /* Success */ printk(KERN_DEBUG "Releasing of cpt module\n"); del_timer(&amp;my_timer); return 0; } static int __init timer_init(void) { /* Registering device */ result = register_chrdev(0, "timer", &amp;timer_fops); if (result &lt; 0) { printk(KERN_DEBUG "timer: cannot obtain major number \n"); return result; } printk(KERN_ALERT "Inserting timer module : %d\n", result); return 0; } static void __exit timer_exit(void) { unregister_chrdev(result, "timer"); printk(KERN_DEBUG "Removing timer module\n"); } struct file_operations timer_fops = { owner: THIS_MODULE, open: timer_open, release: timer_release }; /* Declaration of the init and exit functions */ module_init(timer_init); module_exit(timer_exit); </code></pre> <p>Sorry for my bad english</p>
    singulars
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload