Blame view
samples/kfifo/inttype-example.c
3.74 KB
5bf2b1932 kfifo: add exampl... |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 |
/* * Sample kfifo int type implementation * * Copyright (C) 2010 Stefani Seibold <stefani@seibold.net> * * Released under the GPL version 2 only. * */ #include <linux/init.h> #include <linux/module.h> #include <linux/proc_fs.h> #include <linux/mutex.h> #include <linux/kfifo.h> /* * This module shows how to create a int type fifo. */ /* fifo size in elements (ints) */ #define FIFO_SIZE 32 /* name of the proc entry */ #define PROC_FIFO "int-fifo" /* lock for procfs read access */ static DEFINE_MUTEX(read_lock); /* lock for procfs write access */ static DEFINE_MUTEX(write_lock); /* * define DYNAMIC in this example for a dynamically allocated fifo. * * Otherwise the fifo storage will be a part of the fifo structure. */ #if 0 #define DYNAMIC #endif #ifdef DYNAMIC static DECLARE_KFIFO_PTR(test, int); #else static DEFINE_KFIFO(test, int, FIFO_SIZE); #endif |
a25effa4d kfifo: add explic... |
46 47 48 49 50 51 |
static const int expected_result[FIFO_SIZE] = { 3, 4, 5, 6, 7, 8, 9, 0, 1, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, }; |
5bf2b1932 kfifo: add exampl... |
52 53 54 |
static int __init testfunc(void) { int buf[6]; |
a25effa4d kfifo: add explic... |
55 |
int i, j; |
5bf2b1932 kfifo: add exampl... |
56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 |
unsigned int ret; printk(KERN_INFO "int fifo test start "); /* put values into the fifo */ for (i = 0; i != 10; i++) kfifo_put(&test, &i); /* show the number of used elements */ printk(KERN_INFO "fifo len: %u ", kfifo_len(&test)); /* get max of 2 elements from the fifo */ ret = kfifo_out(&test, buf, 2); printk(KERN_INFO "ret: %d ", ret); /* and put it back to the end of the fifo */ ret = kfifo_in(&test, buf, ret); printk(KERN_INFO "ret: %d ", ret); |
a25effa4d kfifo: add explic... |
77 78 79 80 81 82 83 84 |
/* skip first element of the fifo */ printk(KERN_INFO "skip 1st element "); kfifo_skip(&test); /* put values into the fifo until is full */ for (i = 20; kfifo_put(&test, &i); i++) ; |
5bf2b1932 kfifo: add exampl... |
85 86 87 88 89 90 91 92 |
printk(KERN_INFO "queue len: %u ", kfifo_len(&test)); /* show the first value without removing from the fifo */ if (kfifo_peek(&test, &i)) printk(KERN_INFO "%d ", i); |
a25effa4d kfifo: add explic... |
93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 |
/* check the correctness of all values in the fifo */ j = 0; while (kfifo_get(&test, &i)) { printk(KERN_INFO "item = %d ", i); if (i != expected_result[j++]) { printk(KERN_WARNING "value mismatch: test failed "); return -EIO; } } if (j != ARRAY_SIZE(expected_result)) { printk(KERN_WARNING "size mismatch: test failed "); return -EIO; } printk(KERN_INFO "test passed "); |
5bf2b1932 kfifo: add exampl... |
111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 |
return 0; } static ssize_t fifo_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos) { int ret; unsigned int copied; if (mutex_lock_interruptible(&write_lock)) return -ERESTARTSYS; ret = kfifo_from_user(&test, buf, count, &copied); mutex_unlock(&write_lock); return ret ? ret : copied; } static ssize_t fifo_read(struct file *file, char __user *buf, size_t count, loff_t *ppos) { int ret; unsigned int copied; if (mutex_lock_interruptible(&read_lock)) return -ERESTARTSYS; ret = kfifo_to_user(&test, buf, count, &copied); mutex_unlock(&read_lock); return ret ? ret : copied; } static const struct file_operations fifo_fops = { .owner = THIS_MODULE, .read = fifo_read, .write = fifo_write, |
6038f373a llseek: automatic... |
151 |
.llseek = noop_llseek, |
5bf2b1932 kfifo: add exampl... |
152 153 154 155 156 157 158 159 160 161 162 163 164 165 |
}; static int __init example_init(void) { #ifdef DYNAMIC int ret; ret = kfifo_alloc(&test, FIFO_SIZE, GFP_KERNEL); if (ret) { printk(KERN_ERR "error kfifo_alloc "); return ret; } #endif |
a25effa4d kfifo: add explic... |
166 167 168 169 170 171 |
if (testfunc() < 0) { #ifdef DYNAMIC kfifo_free(&test); #endif return -EIO; } |
5bf2b1932 kfifo: add exampl... |
172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 |
if (proc_create(PROC_FIFO, 0, NULL, &fifo_fops) == NULL) { #ifdef DYNAMIC kfifo_free(&test); #endif return -ENOMEM; } return 0; } static void __exit example_exit(void) { remove_proc_entry(PROC_FIFO, NULL); #ifdef DYNAMIC kfifo_free(&test); #endif } module_init(example_init); module_exit(example_exit); MODULE_LICENSE("GPL"); MODULE_AUTHOR("Stefani Seibold <stefani@seibold.net>"); |