⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 staticram.c

📁 ARM9200在LINUX2.4.19下的SRAM K6X4008T的驱动程序,可以直接加载使用
💻 C
字号:
/* driver/char/staticram.c 
 * 
 * This file provide IO reading and writing from user space.
 * Pls create some device file in diretory /dev/ppcflash whose major is 218.
 * This driver support 0-255 devices. In user space user can read and write
 * IO through open and ioctl function provided by glibc.
 * 
 * Sun Qigang 2007-4-1 
 */
#include <linux/fs.h>
#include <linux/iobuf.h>
#include <linux/major.h>
#include <linux/blkdev.h>
#include <linux/capability.h>
#include <linux/smp_lock.h>
#include <asm/uaccess.h>
#include <asm/hardware.h>
#include <asm/arch/AT91RM9200.h>
#include <asm/io.h>
#include <linux/vmalloc.h>
#include <linux/module.h>#include <linux/mm.h>#include <linux/wrapper.h>	/* mem_map_(un)reserve */#include <linux/slab.h>	/* kmalloc and kfree */

#define STATICRAM_MAJOR 226
#define STATICRAM_ADDR 0x80000000#define STATICRAM_SIZE	0x80000
typedef char staticram_device_t;
static devfs_handle_t staticram_devfs_dir;

static staticram_device_t staticram_devices[256];
static long v_addr = 0;	/* read and write address */
static int	staticram_open(struct inode *, struct file *);
static int	staticram_release(struct inode *, struct file *);
static int	staticram_ctl_ioctl(struct inode *, struct file *, unsigned int, unsigned long);
static ssize_t staticram_read(struct file * file, char * buf, size_t count,  loff_t *ppos);static ssize_t staticram_write(struct file * file, const char * buf, size_t count,  loff_t *ppos);static int staticram_mmap(struct file *file, struct vm_area_struct *vma);


//#################################################################
static struct file_operations staticram_ctl_fops = {
	open:		staticram_open,
	read:		staticram_read,
	write:		staticram_write,	mmap:		staticram_mmap,
	ioctl:		staticram_ctl_ioctl,	release:		staticram_release,
};
static int staticram_open(struct inode *inode, struct file *filp)
{
	int minor;
	minor = MINOR(inode->i_rdev);
	printk("staticram open ok\n");
	staticram_devices[minor]++;
	return 0;
}

static ssize_t staticram_read(struct file * file, char * buf, size_t count, loff_t *ppos)
{		ssize_t read;	unsigned char *staticram_read_val;	int i;	if (count > 0x80000)		count = 0x80000;	read = 0;	(void *)v_addr = ioremap(STATICRAM_ADDR, 0x80000);	staticram_read_val = (char *)kmalloc(count, GFP_KERNEL);	for(i=0; i<count; i++)	{		*(staticram_read_val + i) = (*(volatile unsigned int *)(v_addr + i));		printk(":::0x%01x \n",*(staticram_read_val + i));	}	// if (copy_to_user(buf, __va(p), count))	if (copy_to_user(buf, staticram_read_val, count))		return -EFAULT;	read += count;	kfree(staticram_read_val);	iounmap((void *)v_addr);	return read;}

static ssize_t staticram_write(struct file * file, const char * buf, size_t count,  loff_t *ppos)
{
	ssize_t written;	unsigned char *staticram_write_val;	int i;		if (count > 0x80000)		count = 0x80000;			written = 0;		staticram_write_val = (char *)kmalloc(count, GFP_KERNEL);	if (copy_from_user(staticram_write_val, (void *)buf, count))		return -EFAULT;	(void *)v_addr = ioremap(STATICRAM_ADDR, 0x80000);		for(i=0; i<count; i++)	{		*(volatile unsigned int *)(v_addr + i) = *(staticram_write_val + i);		// printk("::::::0x%01x \n",*(staticram_write_val + i));	}	written += count;	kfree(staticram_write_val);	iounmap((void *)v_addr);	return written;}

static int staticram_release(struct inode *inode, struct file *filp)
{
	int minor;	
	minor = MINOR(inode->i_rdev);
	if (staticram_devices[minor])
		staticram_devices[minor]--;
	printk("staticram release ok\n");
	return 0;
}
static int staticram_mmap(struct file *file, struct vm_area_struct *vma)
{	unsigned long off = vma->vm_pgoff << PAGE_SHIFT;	unsigned long physical = STATICRAM_ADDR + off;	unsigned long vsize = vma->vm_end - vma->vm_start;	unsigned long psize = STATICRAM_SIZE - off;	if (vsize > psize)	{		printk("size too big\n");			return -EINVAL;	//spans too high	}	vma->vm_flags |= VM_IO | VM_RESERVED | VM_LOCKED;	vma->vm_page_prot = pgprot_noncached(vma->vm_page_prot);	remap_page_range(vma->vm_start, physical, vsize, vma->vm_page_prot);	return 0;}
static int staticram_ctl_ioctl(struct inode *inode, 
		  struct file *flip,
		  unsigned int command, 
		  unsigned long arg)
{
	int err = 0;
#if 0
	switch (command) {
	case ADDR:
		
		return 0;		
	case WRITE:
		
		return 0;
	case READ:
		return 0;
	default:
		err = -EINVAL;
	}
#endif
	return err;
}

static int __init staticram_init (void)
{
	//	register_chrdev(STATICRAM_MAJOR, "staticram", &staticram_ctl_fops);
	//############################################################################
	//
	//The" devfs"is very important!!!register file command
	//note:devfs and register ;but ,devfs= register+mknod
	//Here isn't use :mknod  /dev/staticram c 226 0	/* Setup CS7 */	AT91_SYS->PIOC_PDR |= AT91C_PIO_PC13;	AT91_SYS->PIOC_ASR |= AT91C_PC13_NCS7;	// Initialization of the Static Memory Controller for Chip Select 7 (0x00005083)--(0x0000428a)	/* AT91_SYS->EBI_SMC2_CSR[7] = (AT91C_SMC2_NWS & 0x04) | AT91C_SMC2_WSEN | 	*	(AT91C_SMC2_TDF & 0x000) | AT91C_SMC2_DBW_8 | (AT91C_SMC2_RWSETUP & 0x01000000)	*	| (AT91C_SMC2_RWHOLD & 0x10000000); */	AT91_SYS->EBI_SMC2_CSR[7] = (AT91C_SMC2_NWS & 0x0a) | AT91C_SMC2_WSEN		| (AT91C_SMC2_TDF & 0x200) | AT91C_SMC2_DBW_8;        staticram_devfs_dir= devfs_register(NULL,"staticram",DEVFS_FL_DEFAULT,STATICRAM_MAJOR,
                             0, S_IFCHR |S_IRUSR |S_IWUSR |S_IRGRP |S_IWGRP,
                             &staticram_ctl_fops, NULL);
	printk ("staticram driver installed OK. \n");
        
        return 0;
}

static void __exit staticram_exit(void)
{	//iounmap((void *)v_addr);
        devfs_unregister(staticram_devfs_dir);
        printk("staticram driver uninstalled OK. \n");
}


module_init(staticram_init);
module_exit(staticram_exit);

MODULE_LICENSE("GPL");
MODULE_AUTHOR("sqg");
MODULE_DESCRIPTION("staticram Driver for rm9200");

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -