背光驱动内核层及驱动层分析

来源:互联网 发布:淄博双轨制直销软件 编辑:程序博客网 时间:2024/06/05 19:41

一些重要的结构体:

struct mt65xx_led_data {

         structled_classdev cdev;

         structcust_mt65xx_led cust;

         structwork_struct work;

         intlevel;

         intdelay_on;

         intdelay_off;

};

struct led_classdev {

         constchar                  *name;

         int                       brightness;

         int                       max_brightness;

         int                       flags;

 

         /*Lower 16 bits reflect status */

#define LED_SUSPENDED                  (1 << 0)

         /*Upper 16 bits reflect control information */

#define LED_CORE_SUSPENDRESUME   (1 << 16)

#define LED_BLINK_ONESHOT        (1 << 17)

#define LED_BLINK_ONESHOT_STOP      (1 << 18)

#define LED_BLINK_INVERT   (1 << 19)

 

         /*Set LED brightness level */

         /*Must not sleep, use a workqueue if needed */

         void           (*brightness_set)(struct led_classdev*led_cdev,

                                                 enumled_brightness brightness);

         /*Get LED brightness level */

         enumled_brightness (*brightness_get)(struct led_classdev *led_cdev);

 

         /*

          * Activate hardware accelerated blink, delaysare in milliseconds

          * and if both are zero then a sensible defaultshould be chosen.

          * The call should adjust the timings in thatcase and if it can't

          * match the values specified exactly.

          * Deactivate blinking again when thebrightness is set to a fixed

          * value via the brightness_set() callback.

          */

         int              (*blink_set)(struct led_classdev*led_cdev,

                                          unsigned long *delay_on,

                                          unsigned long *delay_off);

 

         structdevice             *dev;

         structlist_head        node;                        /* LED Device list */

         constchar                  *default_trigger;     /* Trigger to use */

 

         unsignedlong           blink_delay_on,blink_delay_off;

         structtimer_list       blink_timer;

         int                       blink_brightness;

 

         structwork_struct  set_brightness_work;

         int                       delayed_set_value;

 

#ifdef CONFIG_LEDS_TRIGGERS

         /*Protects the trigger data below */

         structrw_semaphore      trigger_lock;

 

         structled_trigger    *trigger;

         structlist_head        trig_list;

         void                    *trigger_data;

         /*true if activated - deactivate routine uses it to do cleanup */

         bool                    activated;

#endif

};

 

struct cust_mt65xx_led {

         char                 *name;

         enummt65xx_led_mode  mode;

         long                   data;

 struct PWM_config config_data;

};

 

struct work_struct {

         atomic_long_tdata;

         structlist_head entry;

         work_func_tfunc;

#ifdef CONFIG_LOCKDEP

         structlockdep_map lockdep_map;

#endif

};

 

 

 

 

 

 

 

 

Linux的背光驱动层

Probe:驱动函数

mt65xx_leds_probe

                   //设置全局数组g_leds_data

                   g_leds_data[i]->cust.mode= cust_led_list[i].mode;

                   …….

                   g_leds_data[i]->cdev.brightness_set= mt65xx_led_set;

                                               mt_mt65xx_led_set     //(leds.c)

                                                        schedule_work(&led_data->work);

                                                                 mt_mt65xx_led_set_cust

 

INIT_WORK(&g_leds_data[i]->work,mt_mt65xx_led_work);

ret =led_classdev_register(&pdev->dev, &g_leds_data[i]->cdev);  //led-class.c里定义

if (strcmp(g_leds_data[i]->cdev.name,"lcd-backlight") == 0) {

                            rc= device_create_file(g_leds_data[i]->cdev.dev, &dev_attr_duty);

                            if(rc) {

                                     LEDS_DRV_DEBUG("[LED]device_create_fileduty fail!\n");

                            }

                            ……………..

 

ret =led_classdev_register(&pdev->dev, &g_leds_data[i]->cdev);  //led-class.c里定义

         led_cdev->dev= device_create(leds_class, parent, 0, led_cdev,"%s",led_cdev->name);

         //实现了创建的节点的方法

         staticint __init leds_init(void)

{

         leds_class= class_create(THIS_MODULE, "leds");

         if(IS_ERR(leds_class))

                   returnPTR_ERR(leds_class);

         leds_class->suspend= led_suspend;

         leds_class->resume= led_resume;

         leds_class->dev_attrs= led_class_attrs;

         return0;

}

 

static struct device_attributeled_class_attrs[] = {

         __ATTR(brightness,0644, led_brightness_show, led_brightness_store),

         __ATTR(max_brightness,0444, led_max_brightness_show, NULL),

#ifdef CONFIG_LEDS_TRIGGERS

         __ATTR(trigger,0644, led_trigger_show, led_trigger_store),

#endif

         __ATTR_NULL,

};

 

static ssize_t led_brightness_store(structdevice *dev,

                   structdevice_attribute *attr, const char *buf, size_t size)

{

         structled_classdev *led_cdev = dev_get_drvdata(dev);

         unsignedlong state;

         ssize_tret = -EINVAL;

 

         ret= kstrtoul(buf, 10, &state);

         if(ret)

                   returnret;

 

         if(state == LED_OFF)

                   led_trigger_remove(led_cdev);

         __led_set_brightness(led_cdev,state);  //这里实现了写节点时立马就设置背光的原理

 

         returnsize;

}

 

 

设置背光函数原理:
case MT65XX_LED_MODE_CUST_BLS_PWM:

                   if(strcmp(cust->name, "lcd-backlight") == 0) {

                                     bl_brightness_hal= level;

                            }

                   //mdelay(5000);

                   LEDS_DEBUG("BLSbrightness mapping value:%ld\n",((long)((level*CONFIG_LIGHTNESS_MAPPING_VALUE)/255)));

                   return((cust_set_brightness) (cust->data)) ((long)(level*CONFIG_LIGHTNESS_MAPPING_VALUE/255) );

         //其实调用的是disp_bls_set_backlight函数,cust_leds.c里定义

 

分析disp_bls_set_backlight

disp_bls_set_backlight

                   disp_pwm_set_backlight

                                     disp_pwm_set_backlight_cmdq

                                                        disp_pwm_set_backlight_cmdq

                                                                           level_1024= disp_pwm_level_remap(id, level_1024);

                                                                                             //这里可以设置上层和底层之间的映射

DISP_REG_MASK(cmdq,reg_base + DISP_PWM_CON_1_OFF, level_1024 << 16, 0x1fff << 16);

//设置背光,PWM寄存器配置

 

alps\kernel-3.10\drivers\misc\mediatek\dispsys\mt6735\ddp_pwm.c

0 0
原创粉丝点击