static ssize_t smem_sleep_log_read(struct file *file, char __user *buf,
				size_t len, loff_t *ppos)
{
    struct smem_sleep_log_data *dev = (struct smem_sleep_log_data *)file->private_data;
    size_t copy_len =0;
    SMEM_SLEEP_LOG_DEBUG("%s base = 0x%x, len =%d, offset = %d, buf_size=%d \r\n",__FUNCTION__,dev->smem_buf_base, len,dev->buf_offset,dev->buf_size);
    
    if(dev->buf_offset >= dev->buf_size)
    {
        /*copy is finished */
        return 0; 
    }
    else
    {
       copy_len = ((dev->buf_size - dev->buf_offset) > len) ? len : (dev->buf_size - dev->buf_offset);
    }

    if(NULL != dev->smem_buf_base)
    {   
        /*copy data to user space */
        if(copy_to_user((void __user *)buf, dev->smem_buf_base + dev->buf_offset, copy_len))
        {
            SMEM_SLEEP_LOG_DEBUG("smem_sleep_log_read: Fail to copy memory to user space !\n");
            return -EFAULT;       
        }
        dev->buf_offset += copy_len;
    }
    else
    {
        return -ENOMEM;
    }

	return copy_len;
}
static int smem_sleep_log_open(struct inode *inode, struct file *file)
{
    SMEM_SLEEP_LOG_DEBUG("%s \r\n",__FUNCTION__);
    long buf_len = 0;

    if (down_interruptible(&smem_sleep_log_dev->open_sem))
    {
    	SMEM_SLEEP_LOG_DEBUG(KERN_ERR "smem_open: can not get open_sem!\n");
        return -ERESTARTSYS; 
    }
	file->private_data = smem_sleep_log_dev;
    

    if(NULL == smem_sleep_log_dev->smem_buf_base)
    {
        return -ENOMEM;
    }
    /*get the buffer actul length and actul offset*/
    memcpy(&buf_len,smem_sleep_log_dev->smem_buf_base,sizeof(long));
    smem_sleep_log_dev->buf_size = (buf_len < (smem_buf_size - sizeof(long))) ? buf_len :(smem_buf_size - sizeof(long));
    smem_sleep_log_dev->buf_offset = sizeof(long);
 
	return 0;

}
static int smem_sleep_log_release(struct inode *inode, struct file *file)
{
    SMEM_SLEEP_LOG_DEBUG("%s \r\n",__FUNCTION__);

    up(&smem_sleep_log_dev->open_sem);
	return 0;
}
static ssize_t smem_sleep_log_read(struct file *file, char __user *buf,
				size_t len, loff_t *ppos)
{
    struct smem_log_data *dev = (struct smem_log_data *)file->private_data;
    size_t copy_len =0;
    if(dev->buf_offset >= dev->buf_size)
    {
        /*copy is finished */
        return 0; 
    }
    else
    {
       copy_len = ((dev->buf_size - dev->buf_offset) > len) ? len : (dev->buf_size - dev->buf_offset);
    }

    if(NULL != psmem_buffer)
    {   
        /*copy data to user space */
        if(copy_to_user((void __user *)buf, psmem_buffer + dev->buf_offset, copy_len))
        {
            SMEM_SLEEP_LOG_DEBUG(KERN_ERR "smem_sleep_log_read: Fail to copy memory to user space !\n");
            return -EFAULT;       
        }
        dev->buf_offset += copy_len;
    }
    else
    {
        return -ENOMEM;
    }

	return copy_len;
}
static int smem_sleep_log_open(struct inode *inode, struct file *file)
{
    if (down_interruptible(&smem_log_dev->open_sem))
    {
    	SMEM_SLEEP_LOG_DEBUG(KERN_ERR "smem_open: can not get open_sem!\n");
        return -ERESTARTSYS; 
    }
       
	file->private_data = smem_log_dev; 
    smem_log_dev->buf_size = 0; 
    /*delete 6 lines*/
	return 0;

}
/*not malloc memory by kmalloc any more, and uste the memory get by smem_alloc directly */
static long smem_sleep_log_ioctl(struct file *file, unsigned int cmd,
	unsigned long arg)
{
	int ret = 0;
    struct smem_log_data *dev = (struct smem_log_data *)file->private_data;
    dev->buf_offset = 0;

    switch(cmd)
    {
        /*copy Pwr envent from SMEM to memory*/
        case MSM_SMEM_SLEEP_LOG_IOCTL_GET_PWR_EVENT:
            psmem_buffer = smem_alloc(SMEM_SMEM_LOG_POWER_EVENTS,MAX_SMEM_SLEEP_LOG_EVENT_BUF_SIZE);
            dev->buf_size = MAX_SMEM_SLEEP_LOG_EVENT_BUF_SIZE;        
            if(NULL == psmem_buffer)
            {
                SMEM_SLEEP_LOG_DEBUG(KERN_ERR "smem_sleep_log_ioctl: failed get PWR event\n");
                return -ENOMEM;

            }
            break;
        /*copy sleep voters from SMEM to memory*/
        case MSM_SMEM_SLEEP_LOG_IOCTL_GET_SLEEP_VOTER:
            psmem_buffer = smem_alloc(SMEM_SLEEP_STATIC,MAX_SMEM_SLEEP_VOTER_BUF_SIZE);
            dev->buf_size = MAX_SMEM_SLEEP_VOTER_BUF_SIZE;
            if(NULL == psmem_buffer)
            {
                SMEM_SLEEP_LOG_DEBUG(KERN_ERR "smem_sleep_log_ioctl: failed get Sleep voter\n");
                return -ENOMEM;
            }

            break;
        default: 
            break;
            
    }
	return ret;
}
static int smem_sleep_log_prob(struct platform_device *pdev)
{
    dev_t   dev_id;
    int retval;
    int error;
    unsigned char *mem_base = 0;
        
    smem_sleep_log_dev = kzalloc(sizeof(struct smem_sleep_log_data), GFP_KERNEL);   
    if (!smem_sleep_log_dev)
    {
        SMEM_SLEEP_LOG_DEBUG(KERN_ERR "smem_sleep_log_prob: Unable to alloc memory for device\n"); 
        return (-ENOMEM);
    }

    /* map sleep log memory */
    if ((pdev->id == 0) && (pdev->num_resources > 0)) {
      smem_buf_size = pdev->resource[0].end - pdev->resource[0].start + 1;
	  mem_base = (unsigned char *)(pdev->resource[0].start);
	  
	  SMEM_SLEEP_LOG_DEBUG("%s: phys addr = 0x%x, size = 0x%x\n", __FUNCTION__, mem_base, smem_buf_size);
      smem_sleep_log_dev->smem_buf_base = ioremap((unsigned long)mem_base, (unsigned long)smem_buf_size); 
	  SMEM_SLEEP_LOG_DEBUG("%s: mapped virt address = 0x%x\n", __FUNCTION__, smem_sleep_log_dev->smem_buf_base);
      if (!smem_sleep_log_dev->smem_buf_base)
      {
		printk("smem_sleep_log_prob failed\n");
        return -EBUSY;
      }

    }

    /*init mutex*/
    init_MUTEX(&smem_sleep_log_dev->open_sem); 

    if (major) {
        dev_id = MKDEV(major, 0);
        retval = register_chrdev_region(dev_id, SMEM_SLEEP_LOG_COUNT,
                        NAME);
    } else {
        retval = alloc_chrdev_region(&dev_id, 0, SMEM_SLEEP_LOG_COUNT,
                         NAME);
        major = MAJOR(dev_id);
    }

    if (retval) {
        SMEM_SLEEP_LOG_DEBUG(KERN_ERR "smem_sleep_log cant get major\n");
        kfree(smem_sleep_log_dev);
        return -1;
    }
    
    smem_sleep_log_dev->kt_class = class_create(THIS_MODULE, NAME); 
    if (IS_ERR(smem_sleep_log_dev->kt_class)) 
    {
        SMEM_SLEEP_LOG_DEBUG(KERN_ERR "failed to class_create\n"); 
        goto can_not_create_class; 
    }

    smem_sleep_log_dev->pdevice = device_create(smem_sleep_log_dev->kt_class, NULL, dev_id, "%s", NAME); 
    if (IS_ERR(smem_sleep_log_dev->pdevice)) {
        SMEM_SLEEP_LOG_DEBUG(KERN_ERR "Can't create smem log device\n");
        goto can_not_create_class;
    }

    cdev_init(&(smem_sleep_log_dev->cdev), &smem_sleep_log_fops);
    smem_sleep_log_dev->cdev.owner = THIS_MODULE;
    
    error = cdev_add(&(smem_sleep_log_dev->cdev), dev_id, SMEM_SLEEP_LOG_COUNT);
    if (error) {
        SMEM_SLEEP_LOG_DEBUG(KERN_ERR "smem_sleep_log_prob: Failed  cdev_add\n");
        error = ENOENT;
        goto can_not_add_cdev;
    }
  
    return 0;
    can_not_add_cdev:
       class_unregister(smem_sleep_log_dev->kt_class); 
    can_not_create_class:
       unregister_chrdev_region(dev_id, 1);
       iounmap((void *)(smem_sleep_log_dev->smem_buf_base));
       kfree(smem_sleep_log_dev);
       return error;
}
static int __init smem_sleep_log_init(void)
{
	dev_t	dev_id;
	int	retval;
    int error;
        
	smem_log_dev = kzalloc(sizeof(struct smem_log_data), GFP_KERNEL);	
    if (!smem_log_dev)
    {
        SMEM_SLEEP_LOG_DEBUG(KERN_ERR "smem_sleep_log_init: Unable to alloc memory for device\n"); 
		return (-ENOMEM);
    }


	/*init mutex*/
	init_MUTEX(&smem_log_dev->open_sem); 

	if (major) {
		dev_id = MKDEV(major, 0);
		retval = register_chrdev_region(dev_id, SMEM_SLEEP_LOG_COUNT,
						NAME);
	} else {
		retval = alloc_chrdev_region(&dev_id, 0, SMEM_SLEEP_LOG_COUNT,
					     NAME);
		major = MAJOR(dev_id);
	}

	if (retval) {
        SMEM_SLEEP_LOG_DEBUG(KERN_ERR "smem_sleep_log cant get major\n");
        kfree(smem_log_dev);
		return -1;
	}
    
    smem_log_dev->kt_class = class_create(THIS_MODULE, NAME); 
    if (IS_ERR(smem_log_dev->kt_class)) 
    {
        SMEM_SLEEP_LOG_DEBUG(KERN_ERR "failed to class_create\n"); 
        goto can_not_create_class; 
    }

    smem_log_dev->pdevice = device_create(smem_log_dev->kt_class, NULL, dev_id, "%s", NAME); 
	if (IS_ERR(smem_log_dev->pdevice)) {
		SMEM_SLEEP_LOG_DEBUG(KERN_ERR "Can't create smem log device\n");
		goto can_not_create_class;
	}

	cdev_init(&(smem_log_dev->cdev), &smem_sleep_log_fops);
    smem_log_dev->cdev.owner = THIS_MODULE;
    
	error = cdev_add(&(smem_log_dev->cdev), dev_id, SMEM_SLEEP_LOG_COUNT);
    if (error) {
        SMEM_SLEEP_LOG_DEBUG(KERN_ERR "init_key_test_cdev: Failed  cdev_add\n");
        error = ENOENT;
        goto can_not_add_cdev;
    }
  
    return 0;
    can_not_add_cdev:
       class_unregister(smem_log_dev->kt_class); 
    can_not_create_class:
       unregister_chrdev_region(dev_id, 1);
       kfree(smem_log_dev);
       return error;
}