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

📄 tonedrv.c

📁 A tone driver by driving S3c2410 PWM. Compiled by arm-linux-gcc.
💻 C
字号:
/* Project Name	: ToneSound  * Project Date : 2003/12 * Version	: 0.9 * Program Name	: tonedrv.c   * Description 	: ToneSound Driver  * Author 	: Peter. * Compiler	: arm-linux-gcc*/ #ifndef __KERNEL__#define __KERNEL__#endif#ifndef MODULE#define MODULE#endif#include <linux/fs.h>#include <linux/types.h>#include <linux/module.h>#include <linux/kernel.h>#include <linux/init.h>#include <linux/ioctl.h>#include <asm/system.h>#include <asm/io.h>#include <asm/uaccess.h>#include <asm/irq.h>#include <asm/hardware.h>//#include <asm/asm-s3c2410/s3c2410.h>#include "s3c2410.h"//#include <asm/mach-types.h>//#include <asm/mach-types.h>#define DRIVER_AUTHOR 	"Peter"#define DRIVER_DESC 	"Tone Driver"#define DRIVER_TYPE 	"Tone"#define DRIVER_NAME	"Tone"#define TONE_SOUND	0x67A1#define TONE_VOL	0x67A2#define TONE_STOP	0x67A3#define TONE_MAJOR_NUM	0xFC/* Prototypes */// function used in file_operations int  Tone_init(void);void Tone_cleanup(void);int  Tone_open(struct inode *,struct file *);int  Tone_release(struct inode *,struct file *);int  Tone_ioctl(struct inode *,struct file *,unsigned int cmd,unsigned long arg);ssize_t Tone_read(struct file *,char *,size_t,loff_t *);ssize_t Tone_write(struct file *,const char *,size_t,loff_t *);/* Global Variables */static struct file_operations Tone_fops = {	open: 		Tone_open,	release: 	Tone_release,	read: 		Tone_read,	write: 		Tone_write,	ioctl: 		Tone_ioctl};/* Methods */void Tone_Stop(){	rTCON = ( rTCON & 0xfffffff0 );	}// TCON : [22:0]  =>  Timer0 : TCON[4:0]// TCON[0] : 0:Stop  		1:Start// TCON[1] : 0:No Operation     1:Updat TCNTB0 & TCMPB0// TCON[2] : 0:Invert off 	1: Invert on// TCON[3] : 0:One-Shot 	1: Auto-Reload// TCFG0 : [31:0]  => Prescalar0 : TCFG0[7:0] ( for Timer0 & Timer1) 	// TCFG1 : [31:0]  => MUX0	 : TCFG1[3:0] // 		      0000(1/2)	0001(1/4) 0010(1/8)  0011(1/16)	// TCNTB0: [15:0].	TCMPB0: [15:0]		      		 void Tone_Sound(unsigned long freq){	unsigned int	addr;		rTCFG0 = ((rTCFG0 & ~0x0ff)|0xff);	// Prescalar0 = 255	rTCFG1 = ((rTCFG1 & ~0x0f)| 0x03);	// Divider    = 1/16	rTCNTB0 = freq;				// Between Max_Freq & Min_Freq		rTCMPB0 = rTCNTB0 / 2;	addr = (unsigned int)&rTCON;	printk(KERN_ALERT "Tone_Sound:TCON addr=0x%x\n",addr);	rTCON = ( rTCON & 0xfffffff0 );		rTCON = ( rTCON | 0x08 );				rTCON = ( rTCON & 0xfffffff8 );	rTCON = ( rTCON | 0x0a );	rTCON = ( rTCON & 0xfffffff8 );		rTCON = ( rTCON | 0x08 );	rTCON = ( rTCON & 0xfffffff8 );		rTCON = ( rTCON | 0x09 );}void Tone_Vol(unsigned long vol){	unsigned int addr;		vol &= 0x07;	rGPECON = (rGPECON & ~0x3f)| 0x15;	// GPE0~GPE2 = 01(Output)		rGPEDAT &= 0xfffffff8;	addr = ( unsigned int) &rGPECON;	printk(KERN_ALERT "Tone_Vol:GPECON=0x%x\n",addr);	if ( vol == 1 )		rGPEDAT |= 0x04;	else if ( vol == 2 )		rGPEDAT	|= 0x02;	else if ( vol == 3 )		rGPEDAT |= 0x01;	else 		rGPEDAT &=0xfffffff8;}int Tone_open(struct inode *inode,struct file *flip){	MOD_INC_USE_COUNT;	printk(KERN_ALERT "Tone_Drv:Tone_open\n");	return 0;}int Tone_release(struct inode *inode,struct file *flip){	MOD_DEC_USE_COUNT;		printk(KERN_ALERT "Tone_Drv:Tone_release\n");	return 0;}ssize_t Tone_read(struct file *filp,char *buffer,size_t length,loff_t *offset){	printk(KERN_ALERT "Tone_Drv:Tone_read\n");	return -EINVAL;}ssize_t Tone_write(struct file *filp,const char *buffer,size_t length,loff_t *offset){	printk(KERN_ALERT "Tone_Drv:Tone_write\n");	return -EINVAL;}int Tone_ioctl(struct inode *inode,struct file *file,unsigned int cmd,unsigned long arg){	printk(KERN_ALERT "Tone_Drv:Tone_ioctl=(%x,%u)\n",cmd,(unsigned	int)arg);	switch(cmd) 	{	case TONE_SOUND:			Tone_Sound(arg);			printk(KERN_ALERT "Tone_Drv:ioctl-Sound\n");			return 0;		case TONE_STOP:			Tone_Stop();			printk(KERN_ALERT "Tone_Drv:ioctl-Stop\n");			return 0;					case TONE_VOL:			Tone_Vol(arg);			printk(KERN_ALERT "Tone_Drv:ioctl-Volume\n");			return 0;		default:						return -EINVAL;	}}/*	Functions	*/int Tone_init(void){	int retval;	printk(KERN_ALERT "Tone_Drv:Tone_init... \n");	// register the driver	retval = register_chrdev(TONE_MAJOR_NUM,DRIVER_NAME,&Tone_fops);	if(retval == -1)	{	printk(KERN_ALERT "Tone_Drv:Can't register the Tone Driver\n");	}	else if(retval == 0)	{	printk(KERN_ALERT "Tone_Drv:Register the Tone Driver successfully\n");	}	// Initialize the Tone	Tone_Vol(0);	printk(KERN_ALERT "Tone_Drv: GPBCON = 0x%x\n",(unsigned int)rGPBCON);	rGPBCON &= 0xfffffffc;	rGPBCON |= 0x02;	printk(KERN_ALERT "Tone_Drv: GPBCON = 0x%x\n",(unsigned int)rGPBCON);	return retval;}void Tone_cleanup(void){	int retval;	printk(KERN_ALERT "Tone_Drv:Tone_cleanup- Unloading Tone Driver...\n");	// unregister the driver	retval = unregister_chrdev(TONE_MAJOR_NUM,DRIVER_NAME);	Tone_Stop();	if(retval < 0)	{	printk(KERN_ALERT "Tone_Drv:Can't unregister the Tone Driver\n");	}	else if(retval == 0)	{	printk(KERN_ALERT "Tone_Drv:Unregister the Tone Driver successfully\n");	}	//turn off the Tone Driver}module_init(Tone_init);module_exit(Tone_cleanup);MODULE_LICENSE("GPL");MODULE_AUTHOR(DRIVER_AUTHOR);MODULE_DESCRIPTION(DRIVER_DESC);MODULE_SUPPORTED_DEVICE(DRIVER_TYPE);

⌨️ 快捷键说明

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