Anh Tran / Mbed OS GR-Boards_WebCamera

Dependencies:   HttpServer_snapshot_mbed-os

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers R_BSP_Aio.cpp Source File

R_BSP_Aio.cpp

00001 /*******************************************************************************
00002 * DISCLAIMER
00003 * This software is supplied by Renesas Electronics Corporation and is only
00004 * intended for use with Renesas products. No other uses are authorized. This
00005 * software is owned by Renesas Electronics Corporation and is protected under
00006 * all applicable laws, including copyright laws.
00007 * THIS SOFTWARE IS PROVIDED "AS IS" AND RENESAS MAKES NO WARRANTIES REGARDING
00008 * THIS SOFTWARE, WHETHER EXPRESS, IMPLIED OR STATUTORY, INCLUDING BUT NOT
00009 * LIMITED TO WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE
00010 * AND NON-INFRINGEMENT. ALL SUCH WARRANTIES ARE EXPRESSLY DISCLAIMED.
00011 * TO THE MAXIMUM EXTENT PERMITTED NOT PROHIBITED BY LAW, NEITHER RENESAS
00012 * ELECTRONICS CORPORATION NOR ANY OF ITS AFFILIATED COMPANIES SHALL BE LIABLE
00013 * FOR ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES FOR
00014 * ANY REASON RELATED TO THIS SOFTWARE, EVEN IF RENESAS OR ITS AFFILIATES HAVE
00015 * BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES.
00016 * Renesas reserves the right, without notice, to make changes to this software
00017 * and to discontinue the availability of this software. By using this software,
00018 * you agree to the additional terms and conditions found by accessing the
00019 * following link:
00020 * http://www.renesas.com/disclaimer*
00021 * Copyright (C) 2015 Renesas Electronics Corporation. All rights reserved.
00022 *******************************************************************************/
00023 
00024 #include "cmsis_os.h"
00025 #include "r_typedefs.h"
00026 #include "r_errno.h"
00027 #include "aioif.h"
00028 #include "R_BSP_Aio.h"
00029 
00030 typedef int32_t (*rbsp_read_write_a_func_t)(void* const p_fd, AIOCB* const p_aio, int32_t* const p_errno);
00031 
00032 R_BSP_Aio::R_BSP_Aio() {
00033 }
00034 
00035 R_BSP_Aio::~R_BSP_Aio() {
00036     if (write_ctl.MaxNum != 0) {
00037         delete [] (rbsp_sival_t *)write_ctl.p_sival_top;
00038         delete [] (AIOCB *)write_ctl.p_aio_top;
00039         delete write_ctl.p_sem_ctl;
00040     }
00041     if (read_ctl.MaxNum != 0) {
00042         delete [] (rbsp_sival_t *)read_ctl.p_sival_top;
00043         delete [] (AIOCB *)read_ctl.p_aio_top;
00044         delete read_ctl.p_sem_ctl;
00045     }
00046 }
00047 
00048 void R_BSP_Aio::init(rbsp_serial_ctl_t * p_ctl, void * handle, void * p_func_a, int32_t max_buff_num) {
00049     if (handle != NULL) {
00050         p_ctl->ch_handle    = handle;
00051         p_ctl->MaxNum       = max_buff_num;
00052         p_ctl->p_aio_top    = NULL;
00053         p_ctl->index        = 0;
00054         p_ctl->p_async_func = p_func_a;
00055         if (p_ctl->MaxNum != 0) {
00056             p_ctl->p_sem_ctl    = new Semaphore(p_ctl->MaxNum);
00057             p_ctl->p_aio_top    = new AIOCB[p_ctl->MaxNum];
00058             p_ctl->p_sival_top  = new rbsp_sival_t[p_ctl->MaxNum];
00059         }
00060     }
00061 }
00062 
00063 int32_t R_BSP_Aio::write(void * const p_data, uint32_t data_size, const rbsp_data_conf_t * const p_data_conf) {
00064     if (p_data_conf == NULL) {
00065         return sync_trans(&write_ctl, p_data, data_size);
00066     } else {
00067         return aio_trans(&write_ctl, p_data, data_size, p_data_conf);
00068     }
00069 }
00070 
00071 int32_t R_BSP_Aio::read(void * const p_data, uint32_t data_size, const rbsp_data_conf_t * const p_data_conf) {
00072     if (p_data_conf == NULL) {
00073         return sync_trans(&read_ctl, p_data, data_size);
00074     } else {
00075         return aio_trans(&read_ctl, p_data, data_size, p_data_conf);
00076     }
00077 }
00078 
00079 /* static */ int32_t R_BSP_Aio::sync_trans(rbsp_serial_ctl_t * p_ctl, void * const p_data, uint32_t data_size) {
00080     rbsp_sync_t sync_info;
00081     rbsp_data_conf_t data_conf;
00082     Semaphore * p_sem_wait = new Semaphore(0);
00083 
00084     sync_info.result = -1;
00085     if (p_sem_wait != NULL) {
00086         sync_info.p_sem  = p_sem_wait;
00087 
00088         data_conf.p_notify_func = &callback_sync_trans;
00089         data_conf.p_app_data    = &sync_info;
00090 
00091         if (aio_trans(p_ctl, p_data, data_size, &data_conf) == ESUCCESS) {
00092             p_sem_wait->wait(osWaitForever);
00093         }
00094         delete p_sem_wait;
00095     }
00096 
00097     return sync_info.result;
00098 }
00099 
00100 /* static */ void R_BSP_Aio::callback_sync_trans(void * p_data, int32_t result, void * p_app_data) {
00101     rbsp_sync_t * p_sync_info = (rbsp_sync_t *)p_app_data;
00102 
00103     p_sync_info->result = result;
00104     p_sync_info->p_sem->release();
00105 }
00106 
00107 /* static */ int32_t R_BSP_Aio::aio_trans(rbsp_serial_ctl_t * const p_ctl,
00108                void * const p_data, uint32_t data_size, const rbsp_data_conf_t * const p_data_conf) {
00109     int32_t wk_errno;
00110     AIOCB * p_rbsp_aio;
00111     rbsp_sival_t * p_sival;
00112     rbsp_read_write_a_func_t p_func = (rbsp_read_write_a_func_t)p_ctl->p_async_func;
00113 
00114     if ((p_data_conf == NULL) || (p_data == NULL)) {
00115         wk_errno = ENOSPC_RBSP;
00116     } else if (p_ctl->p_sem_ctl->wait(osWaitForever) == -1) {
00117         wk_errno = EIO_RBSP;
00118     } else {
00119         p_rbsp_aio = (AIOCB *)p_ctl->p_aio_top + p_ctl->index;
00120         p_sival    = p_ctl->p_sival_top + p_ctl->index;
00121 
00122         p_sival->p_cb_func     = p_data_conf->p_notify_func;
00123         p_sival->p_cb_data     = p_data_conf->p_app_data;
00124         p_sival->p_sem         = p_ctl->p_sem_ctl;
00125         p_sival->p_aio         = p_rbsp_aio;
00126 
00127         p_rbsp_aio->aio_fildes = 0;
00128         p_rbsp_aio->aio_buf    = p_data;
00129         p_rbsp_aio->aio_nbytes = data_size;
00130         p_rbsp_aio->aio_offset = 0;
00131         p_rbsp_aio->aio_sigevent.sigev_notify = SIGEV_THREAD;
00132         p_rbsp_aio->aio_sigevent.sigev_value.sival_ptr = (void*)p_sival;
00133         p_rbsp_aio->aio_sigevent.sigev_notify_function = &callback_aio_trans;
00134         p_func(p_ctl->ch_handle, p_rbsp_aio, &wk_errno);
00135 
00136         if (wk_errno == ESUCCESS) {
00137             if ((p_ctl->index + 1) >= p_ctl->MaxNum) {
00138                 p_ctl->index = 0;
00139             } else {
00140                 p_ctl->index++;
00141             }
00142         } else {
00143             p_ctl->p_sem_ctl->release();
00144         }
00145     }
00146 
00147     return wk_errno;
00148 }
00149 
00150 /* static */ void R_BSP_Aio::callback_aio_trans(union sigval signo) {
00151     rbsp_sival_t * p_sival = (rbsp_sival_t *)signo.sival_ptr;
00152     AIOCB * p_aio_result = (AIOCB *)p_sival->p_aio;
00153 
00154     if ((p_sival->p_cb_func != NULL) && (p_aio_result != NULL)) {
00155         p_sival->p_cb_func((void *)p_aio_result->aio_buf, p_aio_result->aio_return, p_sival->p_cb_data);
00156     }
00157     p_sival->p_sem->release();
00158 }