Перейти к содержанию
    

Использование USB virtual_com примера из Kinetis SDK

Добрый день!

 

Прошу помощи по использованию virtual_com USB стека из FRDM-KL26Z_SC: FRDM-KL26Z Sample Code Package

Данный код создает виртуальный ком порт на USB и отображает на терминале вводимые символы. Код собирается без ошибок и работает на железе.

 

Со своим чайниковским уровнем разобраться в этом коде не могу, хочу использовать как черный ящик.

Виртуальный ком порт хочу использовать для вывода данных и дебага своей программы, вместо традиционного UART. Для начала просто вывести строку символов, но даже с этим у меня проблема.

Использование USB принципиально, ради этого все и затевается.

 

Собственно если развернуть этот SDK то интересующий меня пример KSDK1.1.0_KL26Z_KW01Z_1.0.0\usb\example\device\cdc\virtual_com\virtual _com.c

#include "usb_device_config.h"
#include "usb.h"
#include "usb_device_stack_interface.h"
#include "virtual_com.h"
#include "fsl_device_registers.h"
#include "fsl_clock_manager.h"
#include "board.h"
#include "fsl_debug_console.h"
#include "fsl_port_hal.h"
#include <stdio.h>
#include <stdlib.h>
#include "board.h"

/*****************************************************************************
* Constant and Macro's - None
*****************************************************************************/

/*****************************************************************************
* Global Functions Prototypes
*****************************************************************************/
void TestApp_Init(void);

/****************************************************************************
* Global Variables
****************************************************************************/
extern usb_desc_request_notify_struct_t  desc_callback;

cdc_handle_t   g_app_handle;

/*****************************************************************************
* Local Types - None
*****************************************************************************/

/*****************************************************************************
* Local Functions Prototypes
*****************************************************************************/
void USB_App_Device_Callback(uint8_t event_type, void* val,void* arg);
uint8_t USB_App_Class_Callback(uint8_t event, uint16_t value, uint8_t ** data, uint32_t* size, void* arg); 
void Virtual_Com_App(void);
/*****************************************************************************
* Local Variables 
*****************************************************************************/
uint8_t g_line_coding[LINE_CODING_SIZE] = 
{
/*e.g. 0x00,0x10,0x0E,0x00 : 0x000E1000 is 921600 bits per second */
(LINE_CODE_DTERATE_IFACE>> 0) & 0x000000FF,
(LINE_CODE_DTERATE_IFACE>> 8) & 0x000000FF,
(LINE_CODE_DTERATE_IFACE>>16) & 0x000000FF, 		 
(LINE_CODE_DTERATE_IFACE>>24) & 0x000000FF,
 LINE_CODE_CHARFORMAT_IFACE,
 LINE_CODE_PARITYTYPE_IFACE,
 LINE_CODE_DATABITS_IFACE
};

uint8_t g_abstract_state[COMM_FEATURE_DATA_SIZE] = 
{
 (STATUS_ABSTRACT_STATE_IFACE>>0) & 0x00FF,
 (STATUS_ABSTRACT_STATE_IFACE>>8) & 0x00FF																		
};

uint8_t g_country_code[COMM_FEATURE_DATA_SIZE] = 
{
(COUNTRY_SETTING_IFACE>>0) & 0x00FF,
(COUNTRY_SETTING_IFACE>>8) & 0x00FF															  
};
static bool start_app = FALSE;
static bool start_transactions = FALSE;
static uint8_t g_curr_recv_buf[DATA_BUFF_SIZE];
static uint8_t g_curr_send_buf[DATA_BUFF_SIZE];
static uint8_t g_recv_size;
static uint8_t g_send_size;
/*****************************************************************************
* Local Functions
*****************************************************************************/

/**************************************************************************//*!
*
* @name  USB_Get_Line_Coding
*
* @brief The function returns the Line Coding/Configuration
*
* @param handle:        handle     
* @param interface:     interface number     
* @param coding_data:   output line coding data     
*
* @return USB_OK                              When Success
*         USBERR_INVALID_REQ_TYPE             when Error
*****************************************************************************/
uint8_t USB_Get_Line_Coding(uint32_t handle, 
                               uint8_t interface, 
                               uint8_t * *coding_data)
{   
   UNUSED_ARGUMENT(handle)
   /* if interface valid */
   if(interface < USB_MAX_SUPPORTED_INTERFACES)
   {
       /* get line coding data*/
       *coding_data = g_line_coding;
       return USB_OK;  
   }

   return USBERR_INVALID_REQ_TYPE;
}

/**************************************************************************//*!
*
* @name  USB_Set_Line_Coding
*
* @brief The function sets the Line Coding/Configuration
*
* @param handle: handle     
* @param interface:     interface number     
* @param coding_data:   output line coding data     
*
* @return USB_OK                              When Success
*         USBERR_INVALID_REQ_TYPE             when Error
*****************************************************************************/
uint8_t USB_Set_Line_Coding(uint32_t handle, 
                               uint8_t interface, 
                               uint8_t * *coding_data)
{   
   uint8_t count;

   UNUSED_ARGUMENT(handle)

   /* if interface valid */
   if(interface < USB_MAX_SUPPORTED_INTERFACES)
   {
       /* set line coding data*/
       for (count = 0; count < LINE_CODING_SIZE; count++) 
       {          
           g_line_coding[count] = *((*coding_data+USB_SETUP_PKT_SIZE) + count);
       }
       return USB_OK;  
   }

   return USBERR_INVALID_REQ_TYPE;
}

/**************************************************************************//*!
*
* @name  USB_Get_Abstract_State
*
* @brief The function gets the current setting for communication feature
*                                                  (ABSTRACT_STATE)
* @param handle:        handle
* @param interface:     interface number     
* @param feature_data:   output comm feature data     
*
* @return USB_OK                              When Success
*         USBERR_INVALID_REQ_TYPE             when Error
*****************************************************************************/
uint8_t USB_Get_Abstract_State(uint32_t handle, 
                               uint8_t interface, 
                               uint8_t * *feature_data)
{   
   UNUSED_ARGUMENT(handle)
   /* if interface valid */
   if(interface < USB_MAX_SUPPORTED_INTERFACES)
   {
       /* get line coding data*/
       *feature_data = g_abstract_state;
       return USB_OK;  
   }

   return USBERR_INVALID_REQ_TYPE;
}

/**************************************************************************//*!
*
* @name  USB_Get_Country_Setting
*
* @brief The function gets the current setting for communication feature
*                                                  (COUNTRY_CODE)
* @param handle:        handle     
* @param interface:     interface number     
* @param feature_data:   output comm feature data     
*
* @return USB_OK                              When Success
*         USBERR_INVALID_REQ_TYPE             when Error
*****************************************************************************/
uint8_t USB_Get_Country_Setting(uint32_t handle, 
                                   uint8_t interface, 
                                   uint8_t * *feature_data)
{   
   UNUSED_ARGUMENT(handle)
   /* if interface valid */
   if(interface < USB_MAX_SUPPORTED_INTERFACES)
   {
       /* get line coding data*/
       *feature_data = g_country_code;
       return USB_OK;  
   }

   return USBERR_INVALID_REQ_TYPE;
}

/**************************************************************************//*!
*
* @name  USB_Set_Abstract_State
*
* @brief The function gets the current setting for communication feature
*                                                  (ABSTRACT_STATE)
* @param handle:        handle     
* @param interface:     interface number     
* @param feature_data:   output comm feature data     
*
* @return USB_OK                              When Success
*         USBERR_INVALID_REQ_TYPE             when Error
*****************************************************************************/
uint8_t USB_Set_Abstract_State(uint32_t handle, 
                               uint8_t interface, 
                               uint8_t * *feature_data)
{   
   uint8_t count;
   UNUSED_ARGUMENT(handle)
   /* if interface valid */
   if(interface < USB_MAX_SUPPORTED_INTERFACES)
   {
       /* set Abstract State Feature*/
       for (count = 0; count < COMM_FEATURE_DATA_SIZE; count++) 
       {          
           g_abstract_state[count] = *(*feature_data + count);
       }
       return USB_OK; 
   }

   return USBERR_INVALID_REQ_TYPE;
}

/**************************************************************************//*!
*
* @name  USB_Set_Country_Setting
*
* @brief The function gets the current setting for communication feature
*                                                  (COUNTRY_CODE)
* @param handle: handle     
* @param interface:     interface number     
* @param feature_data:   output comm feature data     
*
* @return USB_OK                              When Success
*         USBERR_INVALID_REQ_TYPE             when Error
*****************************************************************************/
uint8_t USB_Set_Country_Setting(uint32_t handle, 
                                   uint8_t interface, 
                                   uint8_t * *feature_data)
{   
   uint8_t count;
   UNUSED_ARGUMENT (handle)

   /* if interface valid */
   if(interface < USB_MAX_SUPPORTED_INTERFACES)
   {
       for (count = 0; count < COMM_FEATURE_DATA_SIZE; count++) 
       {          
           g_country_code[count] = *(*feature_data + count);
       }
       return USB_OK; 
   }

   return USBERR_INVALID_REQ_TYPE;
}
/*****************************************************************************
*  
*	@name		 APP_init
* 
*	@brief		 This function do initialization for APP.
* 
*	@param		 None
* 
*	@return 	 None
**				  
*****************************************************************************/
void APP_init()
{
   cdc_config_struct_t cdc_config;
   cdc_config.cdc_application_callback.callback = USB_App_Device_Callback;
   cdc_config.cdc_application_callback.arg = &g_app_handle;
   cdc_config.vendor_req_callback.callback = NULL;
   cdc_config.vendor_req_callback.arg = NULL;
   cdc_config.class_specific_callback.callback = USB_App_Class_Callback;
   cdc_config.class_specific_callback.arg = &g_app_handle;
   cdc_config.desc_callback_ptr =  &desc_callback;
   /* Always happen in control endpoint hence hard coded in Class layer*/

#if (OS_ADAPTER_ACTIVE_OS == OS_ADAPTER_MQX)
g_curr_recv_buf = OS_Mem_alloc_uncached_align(DATA_BUFF_SIZE, 32);
g_curr_send_buf = OS_Mem_alloc_uncached_align(DATA_BUFF_SIZE, 32);
#endif
   /* Initialize the USB interface */
   USB_Class_CDC_Init(CONTROLLER_ID, &cdc_config, &g_app_handle);
   g_recv_size = 0;
   g_send_size= 0;    
}

/*****************************************************************************
*  
*	@name		 APP_task
* 
*	@brief		 This function runs APP task.
*	@param		 None
* 
*	@return 	 None
**				  
*****************************************************************************/
void APP_task()
{
   while (TRUE) 
   {
       /* call the periodic task function */      
       USB_CDC_Periodic_Task();           

      /*check whether enumeration is complete or not */
       if((start_app==TRUE) && (start_transactions==TRUE))
       {        
           Virtual_Com_App(); 
       }            
   }/* Endwhile */   
}

/******************************************************************************
* 
*    @name       Virtual_Com_App
*    
*    @brief      
*                  
*    @param      None
* 
*    @return     None
*    
*****************************************************************************/
void Virtual_Com_App(void)
{
   /* User Code */ 

   if(g_recv_size) 
   {
       int32_t i;

       /* Copy Buffer to Send Buff */
       for (i = 0; i < g_recv_size; i++)
       {
        //   USB_PRINTF("Copied: %c\n", g_curr_recv_buf[i]);
       	g_curr_send_buf[g_send_size++] = g_curr_recv_buf[i];
       }
       g_recv_size = 0;
   }

   if(g_send_size) 
   {
       uint8_t error;
       uint8_t size = g_send_size;
       g_send_size = 0;

       error = USB_Class_CDC_Send_Data(g_app_handle, DIC_BULK_IN_ENDPOINT,
       	g_curr_send_buf, size);

       if(error != USB_OK) 
       {
           /* Failure to send Data Handling code here */
       } 
   }
   return;
}

/******************************************************************************
* 
*    @name        USB_App_Device_Callback
*    
*    @brief       This function handles the callback  
*                  
*    @param       handle : handle to Identify the controller
*    @param       event_type : value of the event
*    @param       val : gives the configuration value 
* 
*    @return      None
*
*****************************************************************************/
void USB_App_Device_Callback(uint8_t event_type, void* val,void* arg) 
{
   uint32_t handle;
   handle = *((uint32_t *)arg);
   if(event_type == USB_DEV_EVENT_BUS_RESET)
   {
       start_app=FALSE;    
   }
   else if(event_type == USB_DEV_EVENT_CONFIG_CHANGED)
   {
       /* Schedule buffer for receive */
       USB_Class_CDC_Recv_Data(handle, DIC_BULK_OUT_ENDPOINT, g_curr_recv_buf, DIC_BULK_OUT_ENDP_PACKET_SIZE);
       start_app=TRUE;
   }
   else if(event_type == USB_DEV_EVENT_ERROR)
   {
       /* add user code for error handling */
   }
   return;
}

/******************************************************************************
* 
*    @name        USB_App_Class_Callback
*    
*    @brief       This function handles the callback for Get/Set report req  
*                  
*    @param       request  :  request type
*    @param       value    :  give report type and id
*    @param       data     :  pointer to the data 
*    @param       size     :  size of the transfer
*
*    @return      status
*                  USB_OK  :  if successful
*                  else return error
*
*****************************************************************************/

uint8_t USB_App_Class_Callback
(
   uint8_t event, 
   uint16_t value, 
   uint8_t ** data, 
   uint32_t* size,
   void* arg
) 
{
   cdc_handle_t handle;
   uint8_t error = USB_OK;
   handle = *((cdc_handle_t *)arg);
   switch(event)
   {
	case GET_LINE_CODING:
		error = USB_Get_Line_Coding(handle, value, data);
	break;
	case GET_ABSTRACT_STATE:
		error = USB_Get_Abstract_State(handle, value, data);
	break;
	case GET_COUNTRY_SETTING:
		error = USB_Get_Country_Setting(handle, value, data);
	break;
	case SET_LINE_CODING:
		error = USB_Set_Line_Coding(handle, value, data);
	break;
	case SET_ABSTRACT_STATE:
		error = USB_Set_Abstract_State(handle, value, data);
	break;
	case SET_COUNTRY_SETTING:
		error = USB_Set_Country_Setting(handle, value, data);
	break;
	case USB_APP_CDC_DTE_ACTIVATED:
		if(start_app == TRUE)
		{
			start_transactions = TRUE; 
		}
	break;
	case USB_APP_CDC_DTE_DEACTIVATED:
		if(start_app == TRUE)
		{
			start_transactions = FALSE; 
		}
	break;
	case USB_DEV_EVENT_DATA_RECEIVED:
	{
           if((start_app == TRUE) && (start_transactions == TRUE))
           {
			g_recv_size = *size;
			if(!g_recv_size)
			{
				 /* Schedule buffer for next receive event */
				 USB_Class_CDC_Recv_Data(handle, DIC_BULK_OUT_ENDPOINT, g_curr_recv_buf, DIC_BULK_OUT_ENDP_PACKET_SIZE); 
			}

           }
       }
	break;
	case USB_DEV_EVENT_SEND_COMPLETE:
	{
        if ((size != NULL) && (*size != 0) && !(*size % DIC_BULK_IN_ENDP_PACKET_SIZE))
        {
			/* If the last packet is the size of endpoint, then send also zero-ended packet,
			** meaning that we want to inform the host that we do not have any additional
			** data, so it can flush the output.
	             */
            USB_Class_CDC_Send_Data(g_app_handle, DIC_BULK_IN_ENDPOINT, NULL, 0);
        } else if((start_app == TRUE) && (start_transactions == TRUE))
           {
			 if((*data != NULL) || ((*data == NULL) && (*size == 0)))
			 {
				 /* User: add your own code for send complete event */ 
				 /* Schedule buffer for next receive event */
				 USB_Class_CDC_Recv_Data(handle, DIC_BULK_OUT_ENDPOINT, g_curr_recv_buf, DIC_BULK_OUT_ENDP_PACKET_SIZE); 
			 }
           }
	}
	break;
       default:
       error = USBERR_INVALID_REQ_TYPE;
   }

   return error;
}

static void Task_Start(void *arg)
{
       /* call the periodic task function */      
       USB_CDC_Periodic_Task();           

      /*check whether enumeration is complete or not */
       if((start_app==TRUE) && (start_transactions==TRUE))
{
           Virtual_Com_App(); 
   }
}

int main(void)
{
   OSA_Init();
   hardware_init();
   dbg_uart_init();

   APP_init();

   OS_Task_create(Task_Start, NULL, 9L, 1000L, "task_start", NULL);

   OSA_Start();

	USB_PRINTF("Test:\n");

   return 1;
}

/* EOF */

 

Я хочу использовать что-то типа printf который будет выводить в виртуальный порт. В примере даже есть закомментированная строка

 

// USB_PRINTF("Copied: %c\n", g_curr_recv_buf[i]);

 

как я понимаю это какраз то что мне нужно, но если ее раскомментировать то ничего не меняется, если вставить в тело main такое - тоже.

Хотя собирается без ошибок во всех случаях.

Изменено пользователем greenhorn

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Присоединяйтесь к обсуждению

Вы можете написать сейчас и зарегистрироваться позже. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.

Гость
Ответить в этой теме...

×   Вставлено с форматированием.   Вставить как обычный текст

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

×
×
  • Создать...