#include #include #define BUFFER_SIZE 100000 struct demodrv_context { void *buf; }; static void demo_vm_close(struct vm_area_struct *vma) { printk("releasing %p, data = %p\n", vma, vma->vm_private_data); } static struct vm_operations_struct mmap_ops = { .close = demo_vm_close, }; int demo_open_rt(struct rtdm_dev_context *context, rtdm_user_info_t *user_info, int oflags) { struct demodrv_context *my_context; unsigned long vaddr; my_context = (struct demodrv_context *)context->dev_private; my_context->buf = kmalloc(BUFFER_SIZE, 0); /* mark pages reserved so that remap_pfn_range works */ for (vaddr = (unsigned long)my_context->buf; vaddr < (unsigned long)my_context->buf + BUFFER_SIZE; vaddr += PAGE_SIZE) SetPageReserved(virt_to_page(vaddr)); *(int *)my_context->buf = 1234; return 0; } int demo_close_rt(struct rtdm_dev_context *context, rtdm_user_info_t *user_info) { struct demodrv_context *my_context; my_context = (struct demodrv_context *)context->dev_private; printk("%d\n", *((int *)my_context->buf + 1000)); kfree(my_context->buf); return 0; } int demo_ioctl_rt(struct rtdm_dev_context *context, rtdm_user_info_t *user_info, int request, void *arg) { struct demodrv_context *my_context; int err; my_context = (struct demodrv_context *)context->dev_private; printk("buf = %p:%x\n", my_context->buf, *(int *)my_context->buf); err = rtdm_mmap_to_user(user_info, my_context->buf, BUFFER_SIZE, PROT_READ|PROT_WRITE, (void **)arg, &mmap_ops, 0x12345678); printk("rtdm_mmap = %p %d\n", *(void **)arg, err); return 0; } static struct rtdm_device demo_device = { struct_version: RTDM_DEVICE_STRUCT_VER, device_flags: RTDM_NAMED_DEVICE, context_size: sizeof(struct demodrv_context), device_name: "demodev0", open_rt: NULL, open_nrt: demo_open_rt, ops: { close_rt: NULL, close_nrt: demo_close_rt, ioctl_rt: NULL, ioctl_nrt: demo_ioctl_rt, read_rt: NULL, read_nrt: NULL, write_rt: NULL, write_nrt: NULL, recvmsg_rt: NULL, recvmsg_nrt: NULL, sendmsg_rt: NULL, sendmsg_nrt: NULL, }, device_class: RTDM_CLASS_EXPERIMENTAL, device_sub_class: 222, driver_name: "demodrv", peripheral_name: "demodev", provider_name: "-", proc_name: demo_device.device_name, }; int init_module(void) { int ret; ret = rtdm_dev_register(&demo_device); printk("rtdm_dev_register = %d\n", ret); return ret; } void cleanup_module(void) { rtdm_dev_unregister(&demo_device, 1000); }