ssize_t bbd_sensor_write_internal(const char *sensorData, size_t size) { int wr_size; struct bbd_buffer *prxb = NULL; struct bbd_sensor_device* ps = bbd_sensor_ptr(); struct bbd_base* p = bbd_sensor_ptr_base(); if (!p || !ps) return -EINVAL; dprint("%s[%d]\n", __func__, (int) size); prxb = &p->rxb; mutex_lock(&prxb->lock); wr_size = MIN((BBD_MAX_DATA_SIZE - prxb->buff_size), size); memcpy(prxb->pbuff + prxb->buff_size, sensorData, wr_size); prxb->buff_size += wr_size; prxb->count += wr_size; bbd_sensor_write_handshake(ps, prxb); mutex_unlock(&prxb->lock); return wr_size; }
ssize_t bbd_sensor_write(struct file *filp, const char __user *buf, size_t size, loff_t *ppos) { int wr_size = MIN(BBD_MAX_DATA_SIZE, size); struct bbd_buffer *prxb = NULL; struct bbd_sensor_device* ps = bbd_sensor_ptr(); struct bbd_base* p = bbd_sensor_ptr_base(); if (!p || !ps) return -EINVAL; dprint("%s[%d]\n", __func__, (int) size); prxb = &p->rxb; mutex_lock(&prxb->lock); if (copy_from_user(prxb->pbuff, buf, wr_size)) { wr_size = -EFAULT; } else { prxb->buff_size = wr_size; bbd_sensor_write_handshake(ps, prxb); } mutex_unlock(&prxb->lock); return wr_size; }
/** * pull packet from rx_list buffer directly * * @pbuff: buffer pointer * @len : length of pulling data * @timeout_ms: timeout for waiting data in rx_list buffer * if timeout_ms is 0, pull one packet from rx_list buffer directly * * @return: length of buffer, -ETIMEDOUT = timeout */ ssize_t bbd_pull_packet(unsigned char *pbuff, size_t len, unsigned int timeout_ms) { struct bbd_buffer *prxb = NULL; int pull_size = 0; int timeout = 0; struct bbd_base* p = bbd_sensor_ptr_base(); if (!p || pbuff == NULL) return -EINVAL; prxb = &p->rxb; #if 0 //If SSP wants to wait for data and starts read, buff_size can be 0. //So, we should remove following if() clause if (prxb->buff_size <= 0) { printk("error : prxb->buff_size = %d\n", prxb->buff_size); return prxb->buff_size; } #endif if (timeout_ms) { timeout = wait_event_interruptible_timeout( prxb->poll_inq, (prxb->buff_size > 0), msecs_to_jiffies(timeout_ms)); if (!timeout) { //Following line is bug, we should NEVER set buff_size to invalid value like errno. It's bad hack. //prxb->buff_size = -ETIMEDOUT; prxb->buff_size = 0; return -ETIMEDOUT; } } mutex_lock(&prxb->lock); pull_size = MIN(prxb->buff_size, len); memcpy(pbuff, prxb->pbuff, pull_size); prxb->buff_size -= pull_size; //shift. TODO: circ buf { unsigned char *top = prxb->pbuff + pull_size; memcpy(prxb->pbuff, top, prxb->buff_size); } mutex_unlock(&prxb->lock); wake_up(&prxb->comp_inq); return pull_size; }
/** * pull packet from rx_list buffer directly * * @pbuff: buffer pointer * @len : length of pulling data * @timeout_ms: timeout for waiting data in rx_list buffer * if timeout_ms is 0, pull one packet from rx_list buffer directly * * @return: length of buffer, -ETIMEDOUT = timeout */ ssize_t bbd_pull_packet(unsigned char *pbuff, size_t len, unsigned int timeout_ms) { struct bbd_buffer *prxb = NULL; int pull_size = 0; int timeout = 0; struct bbd_base* p = bbd_sensor_ptr_base(); if (!p || pbuff == NULL) return -EINVAL; prxb = &p->rxb; if (prxb->buff_size <= 0) { dprint("error : prxb->buff_size = %d\n", prxb->buff_size); return prxb->buff_size; } if (timeout_ms) { timeout = wait_event_interruptible_timeout( prxb->poll_inq, (prxb->buff_size > 0), msecs_to_jiffies(timeout_ms)); if (!timeout) { dprint("error : timeout for prx->poll_inq\n"); prxb->buff_size = -ETIMEDOUT; return -ETIMEDOUT; } } mutex_lock(&prxb->lock); pull_size = MIN(prxb->buff_size, len); memcpy(pbuff, prxb->pbuff, pull_size); prxb->buff_size -= pull_size; //shift. TODO: circ buf { unsigned char *top = prxb->pbuff + pull_size; memcpy(prxb->pbuff, top, prxb->buff_size); } mutex_unlock(&prxb->lock); wake_up(&prxb->comp_inq); return pull_size; }