📄 usbimage_drv.c
字号:
g_USBImage.txpipe = &g_USBImage.image_ep_in_info->ep_status.epin_status;
g_USBImage.rxpipe = &g_USBImage.image_ep_out_info->ep_status.epout_status;
g_USBImage.intrpipe = &g_USBImage.image_ep_intr_info->ep_status.epin_status;
/* configure DMA setting for EP */
USB_InEPEn(g_USBImage.txpipe->byEP, KAL_TRUE);
/*Non-DMA*/
USB_OutEPEn(g_USBImage.rxpipe->byEP, KAL_FALSE);
USB_InEPEn(g_USBImage.intrpipe->byEP, KAL_FALSE);
/* initialize state machine*/
/* send reset message to usb task, task handles the PTP state machine*/
if (g_USBImage.send_ptp_reset_ilm == KAL_TRUE)
{
kal_uint32 src_mod;
ilm_struct *usb_ilm;
/* avoid sending too many messages to USB task */
g_USBImage.send_ptp_reset_ilm = KAL_FALSE;
if(kal_if_hisr() == KAL_TRUE)
src_mod = MOD_DRV_HISR;
else
src_mod = MOD_USB;
DRV_BuildPrimitive(usb_ilm, src_mod,
MOD_USB, MSG_ID_USB_PTPIMAGE_RESET_IND, NULL);
msg_send_ext_queue(usb_ilm);
}
}
/************************************************************
global variable g_USBImage initialize and release functions
*************************************************************/
/* initialize global variable g_USBImage */
void USB_Init_Image_Status(void)
{
g_USBImage.txpipe = NULL;
g_USBImage.rxpipe = NULL;
g_USBImage.intrpipe = NULL;
g_USBImage.host_cancel_flag = KAL_FALSE;
g_USBImage.send_ptp_reset_ilm = KAL_TRUE;
g_USBImage.mmi_start_job = KAL_FALSE;
g_USBImage.intr_done = KAL_TRUE;
g_USBImage.script_flag = (1<<DDISCVRY);
g_USBImage.current_file_handle = PTP_NO_HANDLE;
g_USBImage.error = KAL_FALSE;
g_USBImage.total_rx_bytes = 0;
g_USBImage.current_rx_bytes = 0;
g_USBImage.total_tx_bytes = 0;
g_USBImage.current_tx_bytes = 0;
g_USBImage.rw_bytes = 0;
g_USBImage.received_xml_size = 0;
g_USBImage.send_xml_size = 0;
/* register handler to handle the EP0 Rx handler */
USB_Register_EP0_RxHdlr(USB_Image_Ep0_Cancel_Hdlr);
}
/* release global variable g_USBImage */
void USB_Release_Image_Status(void)
{
g_USBImage.txpipe = NULL;
g_USBImage.rxpipe = NULL;
g_USBImage.intrpipe = NULL;
g_USBImage.error = KAL_FALSE;
g_USBImage.host_cancel_flag = KAL_FALSE;
g_USBImage.send_ptp_reset_ilm = KAL_TRUE;
g_USBImage.mmi_start_job = KAL_FALSE;
g_USBImage.intr_done = KAL_TRUE;
g_USBImage.script_flag = (1<<DDISCVRY);
if(g_USBImage.current_file_handle >= 0)
{
FS_Close(g_USBImage.current_file_handle);
g_USBImage.current_file_handle = PTP_NO_HANDLE;
}
g_USBImage.total_rx_bytes = 0;
g_USBImage.current_rx_bytes = 0;
g_USBImage.total_tx_bytes = 0;
g_USBImage.current_tx_bytes = 0;
g_USBImage.rw_bytes = 0;
g_USBImage.received_xml_size = 0;
g_USBImage.send_xml_size = 0;
/* release the EP0 Rx handler */
USB_Register_EP0_RxHdlr(NULL);
}
/************************************************************
USB cable plug out handler
*************************************************************/
void USB_Image_Plug_Out_Hdlr()
{
//USB_Image_Send_Msg(USBVIDEO_MSG_MED_STOP_IND, 0, 0);
}
/************************************************************
Tx/Rx path DMA callback function
*************************************************************/
/* RX DMA callback function */
//static void USB_Image_Rx_DMA_Callback(void)
//{
// ilm_struct *usb_ilm;
// usb_image_rx_dma_done_conf_struct *rx_done_conf;
// g_USBImage.rxpipe->nBytesRecv = g_USBImage.rxpipe->nBuffLen;
// USB_Ms_Dbg_Trace(USB_DBG_REC_CALLBACK,0);
/* send a message to usb task, let PTP state machine handle the received data */
// rx_done_conf = (usb_image_rx_dma_done_conf_struct *)construct_local_para(
// sizeof(usb_image_rx_dma_done_conf_struct), TD_CTRL);
// rx_done_conf->pData = g_USBImage.rxpipe->pData;
// rx_done_conf->nBytesRecv = g_USBImage.rxpipe->nBytesRecv;
// DRV_BuildPrimitive(usb_ilm, MOD_DRV_HISR, MOD_USB,
// MSG_ID_USB_PTPIMAGE_DMA_RX_DONE_CONF, rx_done_conf);
// msg_send_ext_queue(usb_ilm);
//}
/* TX DMA callback function */
static void USB_Image_Tx_DMA_Callback(void)
{
if(gUsbDevice.is_configured_now == KAL_TRUE)
{
ilm_struct *usb_ilm;
g_USBImage.txpipe->nBytesLeft = USB_EP_NODATA;
/*send a message to usb task, let PTP state machine handle the transmitted data*/
DRV_BuildPrimitive(usb_ilm, MOD_DRV_HISR, MOD_USB,
MSG_ID_USB_PTPIMAGE_DMA_TX_DONE_CONF, NULL);
msg_send_ext_queue(usb_ilm);
}
}
/************************************************************
Tx/Rx path build functions(use DMA)
*************************************************************/
///* prepare to receive Rx packet to addr and length len */
//void USB_Image_BuildRx(void *addr, kal_uint32 len)
//{
/* stop and ack DMA if previous DMA is not yet ready */
// USB_Stop_DMA_Channel(g_USBImage.rxpipe->byEP);
/* initialize Rx pipe data */
// g_USBImage.rxpipe->pData = (kal_uint8 *)addr;
// g_USBImage.rxpipe->nBytesRecv = 0;
// g_USBImage.rxpipe->nBuffLen = len;
//USB_Ms_Dbg_Trace(USB_DBG_BUILDrecREQ, g_UsbMS.rxpipe->nBuffLen);
/* DMA running state is NOT cleared by USB_Image_Rx_DMA_Callback */
// USB_DMA_Setup(g_USBImage.rxpipe->byEP, USB_OUT_EP_TYPE, (kal_uint32)addr, len,
// USB_Image_Rx_DMA_Callback, KAL_FALSE);
//}
/* prepare to transmit Tx packet from addr and length len */
void USB_Image_BuildTx(void *addr, kal_uint32 len)
{
/* stop and ack DMA if previous DMA is not yet ready */
USB_Stop_DMA_Channel(g_USBImage.txpipe->byEP);
/* initialize Tx pipe*/
g_USBImage.txpipe->pData = (kal_uint8 *)addr;
g_USBImage.txpipe->nBytesLeft = len;
/* dma running state is "NOT" cleared inside the USB_Image_Tx_DMA_Callback function */
USB_DMA_Setup(g_USBImage.txpipe->byEP, USB_IN_EP_TYPE, (kal_uint32)addr, len,
USB_Image_Tx_DMA_Callback, KAL_FALSE);
}
/* prepare to transmit Tx response packet from addr and length len */
void USB_Image_ReturnTx(void *addr, kal_uint32 len)
{
/* stop and ack DMA if previous DMA is not yet ready */
USB_Stop_DMA_Channel(g_USBImage.txpipe->byEP);
/* initialize Tx pipe*/
g_USBImage.txpipe->pData = (kal_uint8 *)addr;
g_USBImage.txpipe->nBytesLeft = len;
/* dma running state is "NOT" cleared inside the USB_Image_Tx_DMA_Callback function */
USB_DMA_Setup(g_USBImage.txpipe->byEP, USB_IN_EP_TYPE, (kal_uint32)addr, len,
NULL, KAL_FALSE);
}
/************************************************************
Utility functions
*************************************************************/
void USB_Send_Null_Packet(kal_uint8 no)
{
kal_bool bEPEmpty;
kal_uint8 count = 0;
/* make sure that previous packets are already sent out
maybe last DMA data has triggered DMA done but data are still in FIFO*/
bEPEmpty = USB_Is_EP_Bulk_In_Empty(no);
/* If cable plug out at this time, add timeout to avoid looping here */
while((bEPEmpty == KAL_FALSE)&&(count != 100))
{
count++;
kal_sleep_task(1);
bEPEmpty = USB_Is_EP_Bulk_In_Empty(no);
}
/* send out a NULL packet */
USB_EPFIFOWrite(no, 0, NULL);
USB_EP_Bulk_In_Ready(no);
/* mak sure previous NULL pkt has been sent out
avoid next DMA data in FIFO sent out instead of previos NULL pkt.*/
bEPEmpty = USB_Is_EP_Bulk_In_Empty(no);
/* If cable plug out at this time, add timeout to avoid looping here */
count = 0;
while((bEPEmpty == KAL_FALSE)&&(count != 100))
{
count++;
kal_sleep_task(1);
bEPEmpty = USB_Is_EP_Bulk_In_Empty(no);
}
}
/* Send interrupt endpoint status packet */
void USB_Image_Send_Intr(void *addr, kal_uint32 len)
{
kal_uint8 count = 0;
kal_uint8 temp_num = 0;
kal_uint8 *index = (kal_uint8*)addr;
/* This flag is used to check whether the previous sent out interrupt packet has been acked */
/* If cable plug out at this time, add timeout to avoid looping here */
while((g_USBImage.intr_done == KAL_FALSE)&&(count != 100))
{
count++;
kal_sleep_task(1);
}
g_USBImage.intr_done = KAL_FALSE;
if ((len/USB_EP_INTR_MAXP) == 0) /* one short packet */
{
USB_EPFIFOWrite(g_USBImage.intrpipe->byEP, len, (kal_uint32*)index);
USB_EP_Bulk_In_Ready(g_USBImage.intrpipe->byEP);
}
else /* (len/USB_EP_INTR_MAXP) >= 1 */
{
while(temp_num != len/USB_EP_INTR_MAXP)
{
USB_EPFIFOWrite(g_USBImage.intrpipe->byEP, USB_EP_INTR_MAXP, (kal_uint32*)index);
USB_EP_Bulk_In_Ready(g_USBImage.intrpipe->byEP);
index += USB_EP_INTR_MAXP;
temp_num++;
/* wait for acked */
count = 0;
while((g_USBImage.intr_done == KAL_FALSE)&&(count != 100))
{
count++;
kal_sleep_task(1);
}
g_USBImage.intr_done = KAL_FALSE;
}
/* send last null or short packet */
if((len%USB_EP_INTR_MAXP) != 0)
{
USB_EPFIFOWrite(g_USBImage.intrpipe->byEP, len%USB_EP_INTR_MAXP, (kal_uint32*)index);
USB_EP_Bulk_In_Ready(g_USBImage.intrpipe->byEP);
}
else
{
/* send out a NULL packet */
USB_EPFIFOWrite(g_USBImage.intrpipe->byEP, 0, NULL);
USB_EP_Bulk_In_Ready(g_USBImage.intrpipe->byEP);
}
}
}
void USB_Image_Cancel_By_Device(void *pdest, kal_uint16 code)
{
PTP_CONTAINER *data = (PTP_CONTAINER *)pdest;
data->ContainerLength = USB_IMAGE_CONTAINER_LENGTH;
data->ContainerType = USB_IMAGE_DATA_BLOCK;
data->Code = code;
data->TransactionID = g_USBImage.current_transactionID;
g_USBImage.error = KAL_TRUE;
g_USBImage.state = PTP_RESPONSE;
g_USBImage.total_tx_bytes = USB_IMAGE_CONTAINER_LENGTH;
USB_Image_BuildTx((void *)data, USB_IMAGE_CONTAINER_LENGTH);
/* cancel transaction interrupt */
g_USBImage.image_event.ContainerLength = USB_IMAGE_CONTAINER_LENGTH;
g_USBImage.image_event.Code = PTP_CANCEL_TRANSACTION;
g_USBImage.image_event.TransactionID = g_USBImage.current_transactionID;
USB_Image_Send_Intr(&g_USBImage.image_event, USB_IMAGE_CONTAINER_LENGTH);
/* object removed interrupt */
g_USBImage.image_event.ContainerLength = USB_IMAGE_RES_1_PARA;
g_USBImage.image_event.Code = PTP_OBJECT_REMOVED;
g_USBImage.image_event.TransactionID = 0xffffffff;
g_USBImage.image_event.Parameter1 = g_USBImage.image_cmd.Parameter1;
USB_Image_Send_Intr(&g_USBImage.image_event, USB_IMAGE_RES_1_PARA);
}
/************************************************************
EP0 command parse functions
*************************************************************/
/* class specific reset command handler */
static void USB_Image_Cmd_Reset(void)
{
USB_Stop_DMA_Channel(g_USBImage.txpipe->byEP);
USB_Clear_IN_EP_FIFO(g_USBImage.txpipe->byEP);
USB_Clear_OUT_EP_FIFO(g_USBImage.rxpipe->byEP);
USB_Clear_IN_EP_FIFO(g_USBImage.intrpipe->byEP);
if (g_USBImage.send_ptp_reset_ilm == KAL_TRUE)
{
ilm_struct *usb_ilm;
/* avoid sending too many messages to USB task */
g_USBImage.send_ptp_reset_ilm = KAL_FALSE;
DRV_BuildPrimitive(usb_ilm, MOD_DRV_HISR, MOD_USB, MSG_ID_USB_PTPIMAGE_RESET_IND, NULL);
msg_send_ext_queue(usb_ilm);
}
}
/* handle the class specific cancellation request */
static void USB_Image_Ep0_Cancel_Hdlr(void *data)
{
kal_uint16 nCount;
kal_uint32 cancel_transaction_ID;
EXT_ASSERT(0, nCount , 0, 0);
/* read the cancel request data block*/
nCount = (kal_uint16)USB_EP0_Pkt_Len();
if(nCount == 6)
{
USB_EPFIFORead(0, 6, &g_USBImage.cancel_block);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -