从应用层设置mx31-pdk板的lcd背光亮度

 

想在应用层自己可调整mx31-pdk板子lcd背光,以便用户能够进行lcd亮度的调整。

    该板子背光通过的电源控制芯片,飞思卡尔自己的13783进行控制,其开发包中已带了电源管理的驱动,包括背光控制的驱动,这里首先略微分析一下该背光驱动代码,然后搞明白应该如何来调节lcd背光亮度。

    首先要找到关于背光控制的驱动代码,经过寻找发现有关电压控制的驱动代码的存放路径为/drivers/mxc/pmic/mc13783/pmic_light.c,浏览该代码可以发现

一.关于驱动的注册的代码

pmic_light.c的最底部有以下代码:

static int __init pmic_light_init(void)

{

       pr_debug("PMIC Light driver loading.../n");

       return platform_driver_register(&pmic_light_driver_ldm);

}

static void __exit pmic_light_exit(void)

{

       platform_driver_unregister(&pmic_light_driver_ldm);

       pr_debug("PMIC Light driver successfully unloaded/n");

}

subsys_initcall(pmic_light_init);

module_exit(pmic_light_exit);

MODULE_DESCRIPTION("PMIC_LIGHT");

从以上代码可看出这里进行了电源管理驱动pmic_light_driver_ldm的注册,而关于这个驱动的定义同样在该文件中,定义为:

static struct platform_driver pmic_light_driver_ldm = {

       .driver = {

                 .name = "pmic_light",

                 },

       .suspend = pmic_light_suspend,

       .resume = pmic_light_resume,

       .probe = pmic_light_probe,

       .remove = pmic_light_remove,

};

其中pmic_light_probe是该驱动注册时要调用的回调函数,这个函数很重要,在这个函数里可以进行设备device的保存,以及资源的获得,以及其他的。

二.Driver驱动pmic_light_probe回调函数阅读

    static int pmic_light_probe(struct platform_device *pdev)

{

       int ret = 0;

       struct class_device *temp_class;

       while (suspend_flag == 1) {

              swait++;

              /* Block if the device is suspended */

              if (wait_event_interruptible(suspendq, (suspend_flag == 0))) {

                     return -ERESTARTSYS;

              }

       }

       pmic_light_major = register_chrdev(0, "pmic_light", &pmic_light_fops);

       if (pmic_light_major < 0) {

              printk(KERN_ERR "Unable to get a major for pmic_light/n");

              return pmic_light_major;

       }

       init_waitqueue_head(&suspendq);

       pmic_light_class = class_create(THIS_MODULE, "pmic_light");

       if (IS_ERR(pmic_light_class)) {

              printk(KERN_ERR "Error creating pmic_light class./n");

              ret = PTR_ERR(pmic_light_class);

              goto err_out1;

       }

       temp_class = class_device_create(pmic_light_class, NULL,

                                    MKDEV(pmic_light_major, 0),

                                    NULL, "pmic_light");

       if (IS_ERR(temp_class)) {

              printk(KERN_ERR "Error creating pmic_light class device./n");

              ret = PTR_ERR(temp_class);

              goto err_out2;

       }

       ret = pmic_light_init_reg();

       if (ret != PMIC_SUCCESS) {

              goto err_out3;

       }

       printk(KERN_INFO "PMIC Light successfully loaded/n");

       return ret;

      err_out3:

       class_device_destroy(pmic_light_class, MKDEV(pmic_light_major, 0));

      err_out2:

       class_destroy(pmic_light_class);

      err_out1:

       unregister_chrdev(pmic_light_major, "pmic_light");

       return ret;

}

可以看出,register_chrdev(0, "pmic_light", &pmic_light_fops)注册了一个字符设备,名字为pmic_ligh,同时指定了它的fileoperations结构体为pmic_light_fops,关于该结构体定义同样子该c文件中,如下:

static struct file_operations pmic_light_fops = {

       .owner = THIS_MODULE,

       .ioctl = pmic_light_ioctl,

       .open = pmic_light_open,

       .release = pmic_light_release,

};

可以看出该设备驱动的用户层操作接口只有三个,还包括打开和关闭的两个必须函数,真正进行操作的函数只有pmic_light_ioctl一个函数。

三.设备驱动pmic_light_ioctl函数阅读

       static int pmic_light_ioctl(struct inode *inode, struct file *file,

                         unsigned int cmd, unsigned long arg)

{

       t_bklit_setting_param *bklit_setting = NULL;

       t_tcled_enable_param *tcled_setting;

       t_fun_param *fun_param;

       t_tcled_ind_param *tcled_ind;

       if (_IOC_TYPE(cmd) != 'p')

              return -ENOTTY;

       switch (cmd) {

       case PMIC_BKLIT_TCLED_ENABLE:

              pmic_bklit_tcled_master_enable();

              break;

       case PMIC_BKLIT_TCLED_DISABLE:

              pmic_bklit_tcled_master_disable();

              break;

       case PMIC_BKLIT_ENABLE:

              pmic_bklit_master_enable();

              break;

       case PMIC_BKLIT_DISABLE:

              pmic_bklit_master_disable();

              break;

       case PMIC_SET_BKLIT:

              if ((bklit_setting = kmalloc(sizeof(t_bklit_setting_param),

                                        GFP_KERNEL)) == NULL) {

                     return -ENOMEM;

              }

              if (copy_from_user(bklit_setting, (t_bklit_setting_param *) arg,

                               sizeof(t_bklit_setting_param))) {

                     kfree(bklit_setting);

                     return -EFAULT;

              }

              CHECK_ERROR_KFREE(pmic_bklit_set_mode(bklit_setting->channel,

                                                bklit_setting->mode),

                              (kfree(bklit_setting)));

              CHECK_ERROR_KFREE(pmic_bklit_set_current(bklit_setting->channel,

                                                  bklit_setting->

                                                  current_level),

                              (kfree(bklit_setting)));

              CHECK_ERROR_KFREE(pmic_bklit_set_dutycycle

                              (bklit_setting->channel,

                               bklit_setting->duty_cycle),

                              (kfree(bklit_setting)));

              CHECK_ERROR_KFREE(pmic_bklit_set_cycle_time

                              (bklit_setting->cycle_time),

                              (kfree(bklit_setting)));

              CHECK_ERROR_KFREE(pmic_bklit_set_boost_mode

                              (bklit_setting->en_dis),

                              (kfree(bklit_setting)));

              CHECK_ERROR_KFREE(pmic_bklit_config_boost_mode

                              (bklit_setting->abms, bklit_setting->abr),

                              (kfree(bklit_setting)));

              if (bklit_setting->edge_slow != false) {

                     CHECK_ERROR_KFREE(pmic_bklit_enable_edge_slow(),

                                     (kfree(bklit_setting)));

              } else {

                     CHECK_ERROR_KFREE(pmic_bklit_disable_edge_slow(),

                                     (kfree(bklit_setting)));

              }

              kfree(bklit_setting);

              break;

       case PMIC_GET_BKLIT:

              if ((bklit_setting = kmalloc(sizeof(t_bklit_setting_param),

                                        GFP_KERNEL)) == NULL) {

                     return -ENOMEM;

              }

              if (copy_from_user(bklit_setting, (t_bklit_setting_param *) arg,

                               sizeof(t_bklit_setting_param))) {

                     kfree(bklit_setting);

                     return -EFAULT;

              }

              CHECK_ERROR_KFREE(pmic_bklit_get_current(bklit_setting->channel,

                                                  &bklit_setting->

                                                  current_level),

                              (kfree(bklit_setting)));

              CHECK_ERROR_KFREE(pmic_bklit_get_cycle_time

                              (&bklit_setting->cycle_time),

                              (kfree(bklit_setting)));

              CHECK_ERROR_KFREE(pmic_bklit_get_dutycycle

                              (bklit_setting->channel,

                               &bklit_setting->duty_cycle),

                              (kfree(bklit_setting)));

              bklit_setting->strobe = BACKLIGHT_STROBE_NONE;

              CHECK_ERROR_KFREE(pmic_bklit_get_mode(bklit_setting->channel,

                                                &bklit_setting->mode),

                              (kfree(bklit_setting)));

              CHECK_ERROR_KFREE(pmic_bklit_get_edge_slow

                              (&bklit_setting->edge_slow),

                              (kfree(bklit_setting)));

              CHECK_ERROR_KFREE(pmic_bklit_get_boost_mode

                              (&bklit_setting->en_dis),

                              (kfree(bklit_setting)));

              CHECK_ERROR_KFREE(pmic_bklit_gets_boost_mode

                              (&bklit_setting->abms, &bklit_setting->abr),

                              (kfree(bklit_setting)));

              if (copy_to_user((t_bklit_setting_param *) arg, bklit_setting,

                             sizeof(t_bklit_setting_param))) {

                     kfree(bklit_setting);

                     return -EFAULT;

              }

              kfree(bklit_setting);

              break;

       case PMIC_RAMPUP_BKLIT:

              CHECK_ERROR(pmic_bklit_rampup((t_bklit_channel) arg));

              break;

       case PMIC_RAMPDOWN_BKLIT:

              CHECK_ERROR(pmic_bklit_rampdown((t_bklit_channel) arg));

              break;

       case PMIC_OFF_RAMPUP_BKLIT:

              CHECK_ERROR(pmic_bklit_off_rampup((t_bklit_channel) arg));

              break;

       case PMIC_OFF_RAMPDOWN_BKLIT:

              CHECK_ERROR(pmic_bklit_off_rampdown((t_bklit_channel) arg));

              break;

                     case STROBE_SLOW:

                     CHECK_ERROR_KFREE(pmic_tcled_fun_strobe

                                     (fun_param->bank, fun_param->channel,

                                      TC_STROBE_SLOW), (kfree(fun_param)));

                     break;

              case STROBE_FAST:

                     CHECK_ERROR_KFREE(pmic_tcled_fun_strobe

                                     (fun_param->bank,

                                      fun_param->channel, TC_STROBE_SLOW),

                                     (kfree(fun_param)));

                     break;

              case CHASING_LIGHT_RGB_SLOW:

                     CHECK_ERROR_KFREE(pmic_tcled_fun_chasinglightspattern

                                     (fun_param->bank, PMIC_RGB, TC_SLOW),

                                     (kfree(fun_param)));

                     break;

       …………………..

………………….

       default:

              return -EINVAL;

       }

       return 0;

}

这是标准的设备驱动函数,为了文章的完整性,这里重述一下上篇文章的关于ioctl的解释。用户的ioctl函数原型为int ioctl(int fd, ind cmd, …),适合对设备的一些特性进行控制,其中fd就是用户程序打开设备时使用open函数返回的文件描述符,cmd就是用户程序对设备的控制命令,至于后面的省略号,那是一些补充参数,一般最多一个,有或没有是和cmd的意义相关的。当需要这个参数时,把该参数的地址传递给static int pmic_battery_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg)arg,以便进行数据的传入和回传(感觉是这样)。所以应用层只用调用标准的函数ioctl(int fd, ind cmd, …)并传递正确的cmd参数就可以了。这里就又有一个重要的事,就是分析以上代码,找出和背光有关的正确的cmd参数。

查看代码有两个case,查看后如下:

case PMIC_BKLIT_ENABLE:

              pmic_bklit_master_enable();////return PMIC_NOT_SUPPORTED;

              break;

       case PMIC_BKLIT_DISABLE:

              pmic_bklit_master_disable();////return PMIC_NOT_SUPPORTED;

              break;

以上俩个函数内容均为return PMIC_NOT_SUPPORTED;从函数内部的return可以看出这俩个命令无效,13783及驱动不支持以上两种操作。

 

关于背光的还有一个很重要的cmd,就是设置背光,如下:

       case PMIC_SET_BKLIT:

              if ((bklit_setting = kmalloc(sizeof(t_bklit_setting_param),

                                        GFP_KERNEL)) == NULL) {

                     return -ENOMEM;

              }

              if (copy_from_user(bklit_setting, (t_bklit_setting_param *) arg,

                               sizeof(t_bklit_setting_param))) {

                     kfree(bklit_setting);

                     return -EFAULT;

              }

      //////以上为读入参数值出现错误返回,若成功后依次执行下边的函数进行模式修改,

              CHECK_ERROR_KFREE(pmic_bklit_set_mode(bklit_setting->channel,

                                                bklit_setting->mode),

                              (kfree(bklit_setting)));

              CHECK_ERROR_KFREE(pmic_bklit_set_current(bklit_setting->channel,

                                                  bklit_setting->current_level),

                              (kfree(bklit_setting)));

              CHECK_ERROR_KFREE(pmic_bklit_set_dutycycle

                              (bklit_setting->channel,

                               bklit_setting->duty_cycle),

                              (kfree(bklit_setting)));

              CHECK_ERROR_KFREE(pmic_bklit_set_cycle_time

                              (bklit_setting->cycle_time),

                              (kfree(bklit_setting)));

              CHECK_ERROR_KFREE(pmic_bklit_set_boost_mode

                              (bklit_setting->en_dis),

                              (kfree(bklit_setting)));

              CHECK_ERROR_KFREE(pmic_bklit_config_boost_mode

                              (bklit_setting->abms, bklit_setting->abr),

                              (kfree(bklit_setting)));

              if (bklit_setting->edge_slow != false) {

                     CHECK_ERROR_KFREE(pmic_bklit_enable_edge_slow(),

                                     (kfree(bklit_setting)));

              } else {

                     CHECK_ERROR_KFREE(pmic_bklit_disable_edge_slow(),

                                     (kfree(bklit_setting)));

              }

              kfree(bklit_setting);

              break;

后边的部分涉及到一个宏定义,在pmic_config.h中进行的定义,如下:

#define CHECK_ERROR_KFREE(func, freeptrs) /

do { /

  int ret = (func); /

  if (ret != PMIC_SUCCESS) /        ////////////如果不成功

  { /

     freeptrs; /                   /////执行free也就是kfree(bklit_setting);

     return ret; /                 ///////并且直接返回.

  }/

} while(0);

可以看出该宏先执行func函数,成功则该宏完成,不成功则kfree(bklit_setting)并返回。可知一连串的CHECK_ERROR_KFREE宏定义实为依次执行各自的func,直到出现错误并立即返回。这里要求要提前把参数t_bklit_setting_param写好,然后通过命令写入寄存器.

关于t_bklit_setting_paramarch-mxc/pmic_light.h有这个定义,如下:

typedef struct {

       t_bklit_channel channel; /*!< Channel */

       t_bklit_mode mode;       /*!< Mode */

       t_bklit_strobe_mode strobe;   /*!< Strobe mode */

       unsigned char current_level;  /*!< Current level */

       unsigned char duty_cycle;     /*!< Duty cycle */

       unsigned char cycle_time;     /*!< Cycle time */

       bool edge_slow;            /*!< Edge Slow */

       bool en_dis;           /*!< Enable disable boost mode */

       unsigned int abms;  /*!< Adaptive boost

                             *   mode selection */

       unsigned int abr;     /*!< Adaptive

                             *   boost reference */

} t_bklit_setting_param;

      

       case PMIC_SET_BKLIT:中调用了很多函数,比如pmic_bklit_set_mode,该文件中有定义:

PMIC_STATUS pmic_bklit_set_mode(t_bklit_channel channel, t_bklit_mode mode)

{

       unsigned int reg_value = 0;

       unsigned int clear_val = 0;

       unsigned int triode_val = 0;

       if (suspend_flag == 1) {

              return -EBUSY;

       }

       CHECK_ERROR(pmic_read_reg(LREG_0, &reg_value, PMIC_ALL_BITS));

       switch (channel) {

       case BACKLIGHT_LED1:

              clear_val = ~(MASK_TRIODE_MAIN_BL);

              triode_val = MASK_TRIODE_MAIN_BL;

              break;

       case BACKLIGHT_LED2:

              clear_val = ~(MASK_TRIODE_MAIN_BL << INDEX_AUXILIARY);

              triode_val = (MASK_TRIODE_MAIN_BL << INDEX_AUXILIARY);

              break;

       case BACKLIGHT_LED3:

              clear_val = ~(MASK_TRIODE_MAIN_BL << INDEX_KEYPAD);

              triode_val = (MASK_TRIODE_MAIN_BL << INDEX_KEYPAD);

              break;

       default:

              return PMIC_PARAMETER_ERROR;

       }

       reg_value = (reg_value & clear_val);

       if (mode == BACKLIGHT_TRIODE_MODE) {

              reg_value = (reg_value | triode_val);

       }

       CHECK_ERROR(pmic_write_reg(LREG_0, reg_value, PMIC_ALL_BITS));

       return PMIC_SUCCESS;

}

分析上边这个函数可以知道t_bklit_channel channel这个参数很重要,直接决定了修改的寄存器的bit位置,t_bklit_channel包含在t_bklit_setting_param参数中,这个参数很重要,但是搜索后没有发现他的初始化内容。

这里很惶惑如何设置这些参数,但又发现可以把初始化好的参数读出来,然后修改后写回就可以了。如下case

case PMIC_GET_BKLIT:

    ……………………

很幸运,在上边的case中发现了可以读出设置的cmd,这样的话可以先读,修改后再写入。

 

 

以上方法虽然可行但并不是一个很好的办法,后来发现, /////pmic_testapp_light.c中的一个函数,

void enable_backlight(int fp, t_bklit_setting_param * setting)

{

       setting->channel = BACKLIGHT_LED1;

       setting->current_level = 4;

       setting->duty_cycle = 7;

       setting->mode = BACKLIGHT_CURRENT_CTRL_MODE;

       setting->cycle_time = 2;

       setting->strobe = BACKLIGHT_STROBE_NONE;

       setting->edge_slow = false;

       setting->en_dis = 0;

       setting->abms = 0;

       setting->abr = 0;

       printf("Main Backlight LED ON./n");

       ioctl(fp, PMIC_SET_BKLIT, setting);

       sleep(1);

       setting->channel = BACKLIGHT_LED2;

       printf("Auxiliary Backlight LED ON./n");

       ioctl(fp, PMIC_SET_BKLIT, setting);

       sleep(1);

       printf("Keypad Backlight LED ON./n");

       setting->channel = BACKLIGHT_LED3;

       ioctl(fp, PMIC_SET_BKLIT, setting);

       /* Check result */

       if(ask_user("Did you see the BACKLIGHTS ON?") == TPASS)

              printf("Test Passed/n");

       else

              printf("Test Failed/n");

}

这样可以确定, setting->channel = BACKLIGHT_LED1对应Main Backlight LED

setting->channel = BACKLIGHT_LED2对应Auxiliary Backlight LED

setting->channel = BACKLIGHT_LED3对应Keypad Backlight LED

lcd的背光应该是Main Backlight LED,这样就可以仿照上边的初始化确定设置了。

 

 

四.参数PMIC_SET_BKLIT等参数的定义

       通过查看代码,在 <asm/arch/pmic_light.h>中有如下定义:

#define PMIC_SET_BKLIT      _IOW('p', 0xe2, int)

#define PMIC_GET_BKLIT      _IOWR('p', 0xe3, int)

………

而在/include/asm-generic/ioctl.h中有如下定义:

#define _IOC_NRBITS  8

#define _IOC_TYPEBITS     8

#define _IOC_SIZEBITS       14

#define _IOC_DIRBITS 2

 

#define _IOC_NRMASK       ((1 << _IOC_NRBITS)-1)

#define _IOC_TYPEMASK   ((1 << _IOC_TYPEBITS)-1)

#define _IOC_SIZEMASK     ((1 << _IOC_SIZEBITS)-1)

#define _IOC_DIRMASK      ((1 << _IOC_DIRBITS)-1)

 

#define _IOC_NRSHIFT       0

#define _IOC_TYPESHIFT   (_IOC_NRSHIFT+_IOC_NRBITS)

#define _IOC_SIZESHIFT    (_IOC_TYPESHIFT+_IOC_TYPEBITS)

#define _IOC_DIRSHIFT      (_IOC_SIZESHIFT+_IOC_SIZEBITS)

 

#define _IOC_NONE     0U

#define _IOC_WRITE   1U

#define _IOC_READ     2U

 

#define _IOC_TYPECHECK(t) /

       ((sizeof(t) == sizeof(t[1]) && /

         sizeof(t) < (1 << _IOC_SIZEBITS)) ? /

         sizeof(t) : __invalid_size_argument_for_IOC)

 

#define _IOC(dir,type,nr,size) /

        (((dir)  << _IOC_DIRSHIFT) | /

         ((type) << _IOC_TYPESHIFT) | /

         ((nr)   << _IOC_NRSHIFT) | /

         ((size) << _IOC_SIZESHIFT))

#define _IOR(type,nr,size)      _IOC(_IOC_READ,(type),(nr),(_IOC_TYPECHECK(size)))

 

以上宏定义完成了对cmd参数PMIC_SET_BKLIT的定义。BACKLIGHT_LED1BACKLIGHT_CURRENT_CTRL_MODEBACKLIGHT_STROBE_NONE等参数在该头文件中也都有定义,可以进行查看,不再详述,会在下边的应用程序中用定义的方法列出。

五.编写程序设置背光

编写一函数light-set.c如下:

#include <sys/types.h>

#include <sys/stat.h>

#include <fcntl.h>

#include <sys/ioctl.h>

#include <unistd.h>

#include <stdio.h>

#include <stdlib.h>

#include <errno.h>

#include <linux/wait.h>

 

#define _IOC_NRBITS  8

#define _IOC_TYPEBITS     8

#define _IOC_SIZEBITS      14

#define _IOC_DIRBITS 2

 

#define _IOC_NRMASK       ((1 << _IOC_NRBITS)-1)

#define _IOC_TYPEMASK   ((1 << _IOC_TYPEBITS)-1)

#define _IOC_SIZEMASK    ((1 << _IOC_SIZEBITS)-1)

#define _IOC_DIRMASK      ((1 << _IOC_DIRBITS)-1)

 

#define _IOC_NRSHIFT       0

#define _IOC_TYPESHIFT   (_IOC_NRSHIFT+_IOC_NRBITS)

#define _IOC_SIZESHIFT    (_IOC_TYPESHIFT+_IOC_TYPEBITS)

#define _IOC_DIRSHIFT     (_IOC_SIZESHIFT+_IOC_SIZEBITS)

 

/*

 * Direction bits.

 */

#define _IOC_NONE     0U

#define _IOC_WRITE   1U

#define _IOC_READ     2U

 

#define _IOC(dir,type,nr,size) /

        (((dir)  << _IOC_DIRSHIFT) | /

         ((type) << _IOC_TYPESHIFT) | /

         ((nr)   << _IOC_NRSHIFT) | /

         ((size) << _IOC_SIZESHIFT))

 

#define _IOC_TYPECHECK(t) /

       ((sizeof(t) == sizeof(t[1]) && /

         sizeof(t) < (1 << _IOC_SIZEBITS)) ? /

         sizeof(t) : __invalid_size_argument_for_IOC)

#define  _IOR(type,nr,size)  _IOC(_IOC_READ,(type),(nr),(_IOC_TYPECHECK(size)))

#define _IOW(type,nr,size)   _IOC(_IOC_WRITE,(type),(nr),(_IOC_TYPECHECK(size)))

#define PMIC_SET_BKLIT                      _IOW('p', 0xe2, int)

#define false 0

#define true 1

typedef enum {

       BACKLIGHT_LED1,            /*! < Backlight channel 1 */

       BACKLIGHT_LED2,            /*! < Backlight channel 2 */

       BACKLIGHT_LED3             /*! < Backlight channel 3 */

} t_bklit_channel;

typedef enum {

       BACKLIGHT_CURRENT_CTRL_MODE,   /*! < Current control mode */

       BACKLIGHT_TRIODE_MODE    /*! < Triode mode */

} t_bklit_mode;

typedef enum {

       /*!

        * No Strobe Light Pulsing

        */

       BACKLIGHT_STROBE_NONE,

       BACKLIGHT_STROBE_FAST,

       BACKLIGHT_STROBE_SLOW

} t_bklit_strobe_mode;

typedef struct {

       t_bklit_channel channel; /*!< Channel */

       t_bklit_mode mode;       /*!< Mode */

       t_bklit_strobe_mode strobe;   /*!< Strobe mode */

       unsigned char current_level;  /*!< Current level */

       unsigned char duty_cycle;     /*!< Duty cycle */

       unsigned char cycle_time;     /*!< Cycle time */

       int edge_slow;        /*!< Edge Slow */  //bool 报错,改为int,

       int en_dis;              /*!< Enable disable boost mode */  //bool 报错,改为int,

       unsigned int abms;  /*!< Adaptive boost

                             *   mode selection */

       unsigned int abr;     /*!< Adaptive

                             *   boost reference */

} t_bklit_setting_param;

main()

{

  int fd,status;

  t_bklit_setting_param setting;

       setting.channel = BACKLIGHT_LED1;

       setting.current_level = 4;

       setting.duty_cycle = 7;

       setting.mode = BACKLIGHT_CURRENT_CTRL_MODE;

       setting.cycle_time = 2;

       setting.strobe = BACKLIGHT_STROBE_NONE;

       setting.edge_slow = false;

       setting.en_dis = 0;

       setting.abms = 0;

       setting.abr = 0;

       /////setting.duty_cycle = 1~15;改变了背光的占空比。

  fd = open("/dev/pmic_light", O_RDWR);

      if (fd < 0) {                         

     printf("/dev/pmic_light  open error!!");

     return -1;

     }

     status =ioctl(fd, PMIC_SET_BKLIT, &setting);

     if (status < 0) {                         

     printf("/dev/pmic_light  set error!!");

     return -1;

     }

      printf("/dev/pmic_light  cycle is  %d!!",setting.duty_cycle);

    return 1; 

}

上边这个应用程序中setting.duty_cycle是关于背光的占空比设置的,可设置为1~15,其中15为百分之百的占空比。数值越小,占空比越小,背光越暗。这样我们通过改变setting.duty_cycle的值,就可以随心所欲的进行背光亮度的调节了。

你可能感兴趣的:(从应用层设置mx31-pdk板的lcd背光亮度)