#include
#include
#include
#include
#include
#include
#include
#include
#define cmd_led_on 1
#define cmd_led_off 0
#define cmd_led_get_state 2
#define leds_num 4
#define s3c24xx_leds_phy_base 0x56000050
#define gpfcon_offset 0x0
#define gpfdat_offset 0x1
#define gpfup_offset 0x2
static int major = 0;
module_param(major, int, s_irugo|s_iwugo);
module_parm_desc(major,"s3c24xx leds major number");
struct s3c24xx_leds_dev ;
struct s3c24xx_leds_dev *devs =null;
static struct class *s3c24xx_leds_class; //建立led 類
static int s3c24xx_leds_open (struct inode *inode, struct file *filp)
static int s3c24xx_leds_close (struct inode *inode, struct file *filp)
static ssize_t s3c24xx_leds_read (struct file * filp, char __user *buf, size_t len, loff_t *loff)
return 0;
}static ssize_t s3c24xx_leds_write (struct file * filp, char __user *buf, size_t len, loff_t *loff)
kbuff = kbuff<<4;
//真正的led操作
// spin_lock(&pdev->spin);
down(&pdev->sem);
if ( pdev->led_state != kbuff ) else }}
}pdev->led_state = kbuff;
// spin_unlock(&pdev->spin);
up(&pdev->sem);
return 0;
}static int s3c24xx_leds_ioctl (struct inode *inode, struct file *filp, unsigned int cmd, unsigned long arg)
switch (cmd)
return 0;
}static struct file_operations s3c24xx_leds_ops = ;
static int __init s3c24xx_leds_init(void)
itmp = register_chrdev(dev_no, "leds", &s3c24xx_leds_ops);
if(itmp < 0)
if( itmp > 0 )
major = itmp;
printk("major = %d\n", major);
s3c24xx_leds_class = class_create(this_module, "leds");//在驅動初始化的**裡呼叫class_create為該裝置建立乙個class,
//再為每個裝置呼叫 class_device_create建立對應的裝置
if(is_err(s3c24xx_leds_class))
#if linux_version_code < kernel_version(2,6,18)
class_device_create(s3c24xx_leds_class,mkdev(major, 0), null, "leds");
#else
device_create(s3c24xx_leds_class,null,mkdev(major, 0), null, "leds");//在/dev目錄下建立相應的裝置節點
#endif
//位址對映
pmem = ioremap(s3c24xx_leds_phy_base, 12);
if (!pmem)
devs->pbase = pmem;
// spin_lock_init(&devs->lock);
//semaphore initialize.
// sem_init(&devs->sem, 1);
init_mutex(&devs->sem);
return 0;
out2:
unregister_chrdev(dev_no, "leds");
out1:
kfree(devs);
out:
return ret;
}static void __exit s3c24xx_leds_exit(void)
module_init(s3c24xx_leds_init);
module_exit(s3c24xx_leds_exit);
module_license("gpl");
module_author("stephenyee([email protected])");
應用程式:
#include
#include
#include
#include
#include
#include
#include
#include
#define leds_name "/dev/leds"
#define cmd_led_on 1
#define cmd_led_off 0
#define cmd_led_get_state 2
#define leds_num 4
int main (int argc, char **argv)
//讀取當前led狀態
ret = read(fd, &buf, 1);
if (ret < 0)
for (i = 0; i< leds_num; i++) {
printf( "led%d state is:%s\n", i+1, buf & (1for (i = 0; i< leds_num; i++) {
printf( "1: led%d state is:%s\n", i+1, buf & (1ioctl (fd, cmd_led_on, 3);
// get state
ret = ioctl (fd, cmd_led_get_state, &leds);
leds &= 0x0f;
printf("ret = %d, leds =%d\n",ret, leds);
for (i = 0; i< leds_num; i++) {
printf( " 3: led%d state is:%s\n", i+1, leds & (1<
訊號量例項
pv原語的含義 p操作和v操作是不可中斷的程式段,稱為原語。pv原語及訊號量的概念都是由荷蘭科學家e.w.dijkstra提出的。訊號量sem是一整數,sem大於等於零時代表可供併發程序使用的資源實體數,但sem小於零時則表示正在等待使用臨界區的程序數。p原語操作的動作是 1 sem減1 2 若se...
訊號量使用例項
include include include include include 2.6.28 module license dual bsd gpl int num 2 5 struct semaphore sem first struct semaphore sem second int thre...
字元裝置驅動 訊號量
訊號量與自旋鎖的區別 當乙個程序試圖去獲取乙個已經鎖住的訊號量時,程序不會像自旋鎖一樣在原地忙等待。而是會將自身進入乙個等待佇列中睡眠,直到擁有訊號量的程序釋放訊號量後等待佇列中的那個程序才被喚醒。不能睡眠的程序不能使用訊號量 驅動程式 使用linux3.2.81核心 include include...