Микроконтроллеры

Информация о пользователе

Привет, Гость! Войдите или зарегистрируйтесь.


Вы здесь » Микроконтроллеры » RA » Blue pill, STM32F103, ШИМ, управляем ДПТ через USB CDC. VNH2SP30.


Blue pill, STM32F103, ШИМ, управляем ДПТ через USB CDC. VNH2SP30.

Сообщений 1 страница 13 из 13

1

CDC взят от сюда USB CDC для STM32F103, все изменения в main().
важно http://www.count-zero.ru/2017/bluepill/
http://s5.uploads.ru/t/MmRqE.png
указанный резистор удаляем, соединяем пин A12 с пином B13 через резистор 1,5 кОм.

Код:
#include "stm32f10x.h"
#include "usblib.h"
#include "string.h"
#include <stdio.h>
#include <stdlib.h>

#define led_usb_on    	(GPIOC->BSRR = GPIO_BSRR_BR13)
#define led_usb_off    	(GPIOC->BSRR = GPIO_BSRR_BS13)
#define usb_on        	(GPIOB->BSRR = GPIO_BSRR_BS13)
#define usb_off        	(GPIOB->BSRR = GPIO_BSRR_BR13)
#define left_on     (GPIOB->BSRR = GPIO_BSRR_BS7)
#define left_off     (GPIOB->BSRR = GPIO_BSRR_BR7)
#define right_on 	(GPIOB->BSRR = GPIO_BSRR_BS8)
#define right_off	(GPIOB->BSRR = GPIO_BSRR_BR8)
#define driver_on         (GPIOB->BSRR = GPIO_BSRR_BS9)
#define driver_off	     (GPIOB->BSRR = GPIO_BSRR_BR9)
/*системный таймер, прерывание каждую мСек */
#define F_CPU     72000000UL	// Тактовая у нас 72МГЦ
#define TimerTick  	F_CPU/1000	// Нам нужен килогерц

USBLIB_WByte _LineState;

/*клок и включение периферии*/
void clk_init( void ){
	RCC->CFGR &= ~RCC_CFGR_SW; // Change System Clock to HSI
  while ((RCC->CFGR & RCC_CFGR_SWS) != 0x00) {
        __NOP();
  };
  RCC->CR &= ~RCC_CR_PLLON; // Disable Pll
  while ((RCC->CR & RCC_CR_PLLON)) {
        __NOP();
  };
  RCC->CFGR &= ~0x3C0000;
  RCC->CFGR |= RCC_CFGR_PLLMULL9; // 6
/*тута можно поиграться чтоб на усб 48 МГц а клок 72МГц*/
//RCC->CFGR |= RCC_CFGR_USBPRE;
  RCC->CFGR |= RCC_CFGR_PLLSRC;
  RCC->CR |= RCC_CR_PLLON;
  while (!(RCC->CR & RCC_CR_PLLON)) {
        __NOP();
	};
  RCC->CFGR |= RCC_CFGR_SW_1; // Change System Clock to PLL
  while ((RCC->CFGR & RCC_CFGR_SWS) != RCC_CFGR_SWS_1) {
        __NOP();
  };
  RCC->APB2ENR |= RCC_APB2ENR_IOPAEN | RCC_APB2ENR_IOPBEN | RCC_APB2ENR_AFIOEN| RCC_APB2ENR_IOPCEN;
}
///////////////////////////////////////////////////////////////////////////////
void usb_pin_usb_led_usb_init(void){
/* ========= PB13 USB CONNECT ========= */
/* PC13 - LED. Output PP */
	GPIOC->CRH |= GPIO_CRH_MODE13_0;
  GPIOC->CRH &= ~GPIO_CRH_CNF13;
/* PA15 - USB EN. Output PP */
  GPIOB->CRH |= GPIO_CRH_MODE13_0;
  GPIOB->CRH &= ~GPIO_CRH_CNF13;
	usb_off;
  for (int i = 0; i < 1000000; i++) {
        __NOP();
    };
  USBLIB_Init();
	usb_on;
	for (int i = 0; i < 1000000; i++) {
        __NOP();
    };
}
//////////////////////////////////////////////////////////////
struct usb {
	char *str_tx;
	char *str_rx;
	volatile uint16_t size_str_tx;
	volatile uint16_t size_str;
	volatile uint16_t size_str_rx;
	volatile uint8_t number_sms;
	volatile _Bool busy_tx;//флаг события передачи - передается
	volatile _Bool ready_tx;
	volatile _Bool ready_rx;
	volatile _Bool rewrite_rx;
}usb ={0,0,0,0,0,0,0,0,0,0};
void SysTick_Handler(void)
{
	/*проверяем свободность ресурса*/
	/*если не занято переносом строки сообщения в буфер передач, или идет передача в усб*/
	if( ( usb.busy_tx == 1 ) && ( usb.ready_tx == 1 ) ){
           /*попали сюда через 1 мСек значит передача завершена*/
           usb.busy_tx = 0;
           usb.ready_tx = 0;
           /*обнулить строку передачи*/
           usb.str_tx = memset( usb.str_tx, NULL, usb.size_str_tx );
           usb.size_str = 0;
           usb.size_str_tx = 0;
	}
	if( ( usb.ready_tx == 1 ) && ( usb.busy_tx == 0 ) ){
            if( _LineState.L ){USBLIB_Transmit((uint16_t *)usb.str_tx, (uint16_t)usb.size_str_tx);}
            usb.busy_tx = 1;
	}
}
int usb_tx( char * str )
{
	if( usb.busy_tx == 1 ){ return 1; }/*занято передачей*/
	usb.size_str = strlen( str ) + 6 ;/*размер строки сообщения*/
	if( ( usb.size_str ) > CDC_DATA_FS_MAX_PACKET_SIZE ){ return -1;}/*ошибка размер сообщения слишком большой*/
	usb.size_str_tx = strlen( usb.str_tx );/*размер строки передачи*/
	if( ( usb.size_str + usb.size_str_tx ) > CDC_DATA_FS_MAX_PACKET_SIZE ){ return 2;}/*ждите освождения не лезет*/
	else{ /* прибавить к строке передачи новое сообщение. поднять флаг готовности данных*/
          sprintf( ( usb.str_tx + usb.size_str_tx ), "%03d", ( int )( ++usb.number_sms ) );/*из переменной в строку*/
          memset( ( usb.str_tx + usb.size_str_tx + 3 ), '\n', 1 );
          memmove( ( usb.str_tx + usb.size_str_tx + 4 ), str , usb.size_str );
          usb.ready_tx = 1;
          return 0;
	}
}
int main(void)
{
	clk_init();
	usb_pin_usb_led_usb_init();
	SysTick_Config(TimerTick);
	usb.str_tx = calloc( CDC_DATA_FS_MAX_PACKET_SIZE, sizeof( char ) );
	usb.str_rx = calloc( CDC_DATA_FS_MAX_PACKET_SIZE, sizeof( char ) );
	while( 1 ){
	    while( usb_tx( "sos\r\n" ) != 0 );
	}
}
void uUSBLIB_DataReceivedHandler( uint16_t *Data, uint16_t Length )
{
	usb.size_str_rx = strlen( usb.str_rx );
	if( ( usb.size_str_rx + Length ) <= CDC_DATA_FS_MAX_PACKET_SIZE ){ 
           memmove( ( usb.str_rx + usb.size_str_rx ), (char*)Data , Length );
           usb.ready_rx = 1;
	}
	else{
           memset( usb.str_rx, NULL, usb.size_str_rx );
           memmove( usb.str_rx , (char*)Data , Length );
           usb.ready_rx = 1;
           usb.rewrite_rx = 1;
	}
}
void uUSBLIB_LineStateHandler(USBLIB_WByte LineState)
{
    if (LineState.L) {      //App connected to the virtual port
        _LineState = LineState;
    }
}

2

тактирование http://s7.uploads.ru/t/9KA8h.png
драйвер http://s5.uploads.ru/t/z4mCi.png http://s9.uploads.ru/t/Hhn3X.png взято тут http://arduinolab.pw/index.php/2017/06/ … -vnh2sp30/
сам модуль http://s7.uploads.ru/t/Y93rO.jpg выход датчика тока не использую... пока... что.

3

Код:
#include "stm32f10x.h"
#include "usblib.h"
#include "string.h"
#include <stdio.h>
#include <stdlib.h>

#define led_usb_on    	(GPIOC->BSRR = GPIO_BSRR_BR13)
#define led_usb_off    	(GPIOC->BSRR = GPIO_BSRR_BS13)
#define usb_on        	(GPIOB->BSRR = GPIO_BSRR_BS13)
#define usb_off        	(GPIOB->BSRR = GPIO_BSRR_BR13)
#define left_on     (GPIOB->BSRR = GPIO_BSRR_BS7)
#define left_off     (GPIOB->BSRR = GPIO_BSRR_BR7)
#define right_on 	(GPIOB->BSRR = GPIO_BSRR_BS8)
#define right_off	(GPIOB->BSRR = GPIO_BSRR_BR8)
#define driver_on         (GPIOB->BSRR = GPIO_BSRR_BS9)
#define driver_off	     (GPIOB->BSRR = GPIO_BSRR_BR9)
/*системный таймер, прерывание каждую мСек */
#define F_CPU     72000000UL	// Тактовая у нас 72МГЦ
#define TimerTick  	F_CPU/1000	// Нам нужен килогерц

USBLIB_WByte _LineState;

/*клок и включение периферии*/
void clk_init( void ){
	RCC->CFGR &= ~RCC_CFGR_SW; // Change System Clock to HSI
  while ((RCC->CFGR & RCC_CFGR_SWS) != 0x00) {
        __NOP();
  };
  RCC->CR &= ~RCC_CR_PLLON; // Disable Pll
  while ((RCC->CR & RCC_CR_PLLON)) {
        __NOP();
  };
  RCC->CFGR &= ~0x3C0000;
  RCC->CFGR |= RCC_CFGR_PLLMULL9; // 6
/*тута можно поиграться чтоб на усб 48 МГц а клок 72МГц*/
//RCC->CFGR |= RCC_CFGR_USBPRE;
  RCC->CFGR |= RCC_CFGR_PLLSRC;
  RCC->CR |= RCC_CR_PLLON;
  while (!(RCC->CR & RCC_CR_PLLON)) {
        __NOP();
	};
  RCC->CFGR |= RCC_CFGR_SW_1; // Change System Clock to PLL
  while ((RCC->CFGR & RCC_CFGR_SWS) != RCC_CFGR_SWS_1) {
        __NOP();
  };
  RCC->APB2ENR |= RCC_APB2ENR_IOPAEN | RCC_APB2ENR_IOPBEN | RCC_APB2ENR_IOPCEN | RCC_APB2ENR_AFIOEN | RCC_APB2ENR_TIM1EN;
	RCC->APB1ENR |= RCC_APB1ENR_TIM2EN;
}
///////////////////////////////////////////////////////////////////////////////
void usb_pin_usb_init(void){
/* ========= PB13 USB CONNECT ========= */
/* PC13 - LED. Output PP */
	GPIOC->CRH |= GPIO_CRH_MODE13_0;
  GPIOC->CRH &= ~GPIO_CRH_CNF13;
/* PA15 - USB EN. Output PP */
  GPIOB->CRH |= GPIO_CRH_MODE13_0;
  GPIOB->CRH &= ~GPIO_CRH_CNF13;
	usb_off;
  for (int i = 0; i < 10000000; i++) {
        __NOP();
    };
  USBLIB_Init();
	usb_on;
	for (int i = 0; i < 10000000; i++) {
        __NOP();
    };
}
//////////////////////////////////////////////////////////////
struct usb_tx {
	char *str_tx;
	volatile uint16_t size_str_tx;
	volatile uint16_t size_str;
	volatile uint8_t number_sms;
	volatile _Bool busy_tx;//флаг события передачи - передается
	volatile _Bool ready_tx;
}usb_tx ={0,0,0,0,0,0};
//////////////////////////////////////////////////////////////
struct usb_rx {
	char *str_rx;
	volatile uint16_t size_str_rx;
	volatile _Bool ready_rx;
	volatile _Bool rewrite_rx;
}usb_rx ={0,0,0,0};
//////////////////////////////////////////////////////////////
void SysTick_Handler(void)
{
	if( ( usb_tx.busy_tx == 1 ) && ( usb_tx.ready_tx == 1 ) ){
    /*попали сюда через 1 мСек значит передача завершена*/
    usb_tx.busy_tx = 0;
    usb_tx.ready_tx = 0;
    /*обнулить строку передачи*/
    usb_tx.str_tx = memset( usb_tx.str_tx, NULL, usb_tx.size_str_tx );
    usb_tx.size_str = 0;
    usb_tx.size_str_tx = 0;
	}
	if( ( usb_tx.ready_tx == 1 ) && ( usb_tx.busy_tx == 0 ) ){
    usb_tx.size_str_tx = strlen( usb_tx.str_tx );
    if( _LineState.L ){USBLIB_Transmit((uint16_t *)usb_tx.str_tx, (uint16_t)usb_tx.size_str_tx);}
    usb_tx.busy_tx = 1;
	}
}
int usb_sms( char * str )
{
	if( usb_tx.busy_tx == 1 ){ return 1; }/*занято передачей*/
	usb_tx.size_str = strlen( str ) + 6 ;/*размер строки сообщения*/
	if( ( usb_tx.size_str ) > CDC_DATA_FS_MAX_PACKET_SIZE ){ return -1;}/*ошибка размер сообщения слишком большой*/
	usb_tx.size_str_tx = strlen( usb_tx.str_tx );/*размер строки передачи*/
	if( ( usb_tx.size_str + usb_tx.size_str_tx ) > CDC_DATA_FS_MAX_PACKET_SIZE ){ return 2;}/*ждите освождения не лезет*/
	else{ /* прибавить к строке передачи новое сообщение. поднять флаг готовности данных*/
    sprintf( ( usb_tx.str_tx + usb_tx.size_str_tx ), "%03d", ( int )( ++usb_tx.number_sms ) );/*из переменной в строку*/
    memset( ( usb_tx.str_tx + usb_tx.size_str_tx + 3 ), '\n', 1 );
    memmove( ( usb_tx.str_tx + usb_tx.size_str_tx + 4 ), str , usb_tx.size_str );
    usb_tx.ready_tx = 1;
    return 0;
	}
}
int init_pwm( uint16_t f_pwm, uint16_t dt1, uint16_t dt2, uint16_t dt3 )
{
	/*Таймер 1, режим ШИМ на три канала
	1 - PA8(CH1)
	2 - PA9(CH2)
	3 - PA10(CH3)*/
  GPIOA->CRH = ( GPIOA->CRH & ~( 
	GPIO_CRH_MODE8 | GPIO_CRH_CNF8 | /*канал 1*/
	GPIO_CRH_MODE9 | GPIO_CRH_CNF9 | /*канал 2*/
	GPIO_CRH_MODE10 | GPIO_CRH_CNF10 /*канал 3*/
	) ) | 
	GPIO_CRH_CNF8_0 | GPIO_CRH_MODE8_1 | GPIO_CRH_MODE8_0 |  /*канал 1 ВЫХОД 50МГЦ АЛЬТ.ФУНКЦИЯ PUSH-PULL*/
	GPIO_CRH_CNF9_0 | GPIO_CRH_MODE9_1 | GPIO_CRH_MODE9_0 |  /*канал 2 ВЫХОД 50МГЦ АЛЬТ.ФУНКЦИЯ PUSH-PULL*/
	GPIO_CRH_CNF10_0 | GPIO_CRH_MODE10_1 | GPIO_CRH_MODE10_0 /*канал 3 ВЫХОД 50МГЦ АЛЬТ.ФУНКЦИЯ PUSH-PULL*/
	;	
	// ШИМ 10кГц
	/* F_CPU/72/f_pwm */
	uint16_t f = (F_CPU/72)/f_pwm;
	TIM1->PSC = 72-1;
  TIM1->ARR = f;
	//коэф. заполнения
	TIM1->CCR1 = dt1;
	TIM1->CCR2 = dt2;
	TIM1->CCR3 = dt3;
	TIM1->CCER |= TIM_CCER_CC1E; /*канал 1*/
	TIM1->CCER |= TIM_CCER_CC2E;/*канал 2*/
	TIM1->CCER |= TIM_CCER_CC3E;/*канал 3*/
	TIM1->BDTR |= TIM_BDTR_MOE;
  TIM1->CCMR1 = TIM_CCMR1_OC1M_2 | TIM_CCMR1_OC1M_1;/*канал 1*/
	TIM1->CCMR1 = TIM_CCMR1_OC2M_2 | TIM_CCMR1_OC2M_1;/*канал 2*/
	TIM1->CCMR2 = TIM_CCMR2_OC3M_2 | TIM_CCMR2_OC3M_1;/*канал 3*/
	TIM1->CR1 &= ~TIM_CR1_DIR;
	TIM1->CR1 &= ~TIM_CR1_CMS;
	TIM1->CR1 |= TIM_CR1_CEN;
	return 0;
}
void set_null_pos( void )
{
	while( usb_sms( "set null-run\r\n" ) != 0 ){};
    /*функция установки нуля по всем осям*/
	while( usb_sms( "set null-done\r\n" ) != 0 ){};
    /*готовность к дальнейшей работе*/
	while( usb_sms( "ready to receive commands\r\n" ) != 0 ){};
}
void sms_rx( void )
{
	if( usb_rx.ready_rx ){
    char *axis = strtok( usb_rx.str_rx, "/=%" );
    if( ( strcmp( "x", axis ) == 0 ) ){while( usb_sms( "axis x\r\n" ) != 0 ){}; goto NOTERROR;}
    if( ( strcmp( "y", axis ) == 0 ) ){while( usb_sms( "axis y\r\n" ) != 0 ){}; goto NOTERROR;}
    if( ( strcmp( "z", axis ) == 0 ) ){while( usb_sms( "axis z\r\n" ) != 0 ){}; goto NOTERROR;}
    if( ( strcmp( "xyz", axis ) == 0 ) ){while( usb_sms( "axis xyz\r\n" ) != 0 ){}; goto NOTERROR;}
    if( ( strcmp( "setup", axis ) == 0 ) ){while( usb_sms( "setup\r\n" ) != 0 ){}; goto NOTERROR;}
    if( ( strcmp( "stop", axis ) == 0 ) ){while( usb_sms( "stop\r\n" ) != 0 ){}; goto NOTERROR;}
    while( usb_sms( "erroneous command\r\n" ) != 0 );
NOTERROR:    
    usb_rx.size_str_rx = strlen( usb_rx.str_rx );
    memset( usb_rx.str_rx, NULL, usb_rx.size_str_rx );
    usb_rx.ready_rx = 0;
	}
}
int main(void)
{
	clk_init();
	usb_pin_usb_init();
	led_usb_off;
	SysTick_Config(TimerTick);
	usb_tx.str_tx = calloc( CDC_DATA_FS_MAX_PACKET_SIZE, sizeof( char ) );
	usb_rx.str_rx = calloc( CDC_DATA_FS_MAX_PACKET_SIZE, sizeof( char ) );
	set_null_pos();
	while( 1 ){
    sms_rx();
	}
}
void uUSBLIB_DataReceivedHandler( uint16_t *Data, uint16_t Length )
{
	usb_rx.size_str_rx = strlen( usb_rx.str_rx );
	if( ( usb_rx.size_str_rx + Length ) <= CDC_DATA_FS_MAX_PACKET_SIZE ){ 
    memmove( ( usb_rx.str_rx + usb_rx.size_str_rx ), (char*)Data , Length );
    usb_rx.ready_rx = 1;
	}
	else{
    memset( usb_rx.str_rx, NULL, usb_rx.size_str_rx );
    memmove( usb_rx.str_rx , (char*)Data , Length );
    usb_rx.ready_rx = 1;
    usb_rx.rewrite_rx = 1;
	}
}
void uUSBLIB_LineStateHandler(USBLIB_WByte LineState)
{
    if (LineState.L) {      //App connected to the virtual port
        _LineState = LineState;
    }
}

4

Код:
#include "stm32f10x.h"
#include "usblib.h"
#include "string.h"
#include <stdio.h>
#include <stdlib.h>

#define led_usb_on    	(GPIOC->BSRR = GPIO_BSRR_BR13)
#define led_usb_off    	(GPIOC->BSRR = GPIO_BSRR_BS13)
#define usb_on        	(GPIOB->BSRR = GPIO_BSRR_BS13)
#define usb_off        	(GPIOB->BSRR = GPIO_BSRR_BR13)
#define left_on     (GPIOB->BSRR = GPIO_BSRR_BS7)
#define left_off     (GPIOB->BSRR = GPIO_BSRR_BR7)
#define right_on 	(GPIOB->BSRR = GPIO_BSRR_BS8)
#define right_off	(GPIOB->BSRR = GPIO_BSRR_BR8)
#define driver_on         (GPIOB->BSRR = GPIO_BSRR_BS9)
#define driver_off	     (GPIOB->BSRR = GPIO_BSRR_BR9)
/*системный таймер, прерывание каждую мСек */
#define F_CPU     72000000UL	// Тактовая у нас 72МГЦ
#define TimerTick  	F_CPU/1000	// Нам нужен килогерц

USBLIB_WByte _LineState;

/*клок и включение периферии*/
void clk_init( void ){
	RCC->CFGR &= ~RCC_CFGR_SW; // Change System Clock to HSI
  while ((RCC->CFGR & RCC_CFGR_SWS) != 0x00){ __NOP(); }
  RCC->CR &= ~RCC_CR_PLLON; // Disable Pll
  while ((RCC->CR & RCC_CR_PLLON)){ __NOP(); }
  RCC->CFGR &= ~0x3C0000;
  RCC->CFGR |= RCC_CFGR_PLLMULL9; // 6
/*тута можно поиграться чтоб на усб 48 МГц а клок 72МГц*/
//RCC->CFGR |= RCC_CFGR_USBPRE;
  RCC->CFGR |= RCC_CFGR_PLLSRC;
  RCC->CR |= RCC_CR_PLLON;
  while (!(RCC->CR & RCC_CR_PLLON)){ __NOP(); }
  RCC->CFGR |= RCC_CFGR_SW_1; // Change System Clock to PLL
  while ((RCC->CFGR & RCC_CFGR_SWS) != RCC_CFGR_SWS_1){ __NOP(); }
  RCC->APB2ENR |= RCC_APB2ENR_IOPAEN | RCC_APB2ENR_IOPBEN | RCC_APB2ENR_IOPCEN | RCC_APB2ENR_AFIOEN | RCC_APB2ENR_TIM1EN;
	RCC->APB1ENR |= RCC_APB1ENR_TIM2EN;
}
///////////////////////////////////////////////////////////////////////////////
void usb_pin_usb_init(void)
{
/* ========= PB13 USB CONNECT ========= */
/* PC13 - LED. Output PP */
	GPIOC->CRH |= GPIO_CRH_MODE13_0;
  GPIOC->CRH &= ~GPIO_CRH_CNF13;
/* PA15 - USB EN. Output PP */
  GPIOB->CRH |= GPIO_CRH_MODE13_0;
  GPIOB->CRH &= ~GPIO_CRH_CNF13;
	usb_off;
  for (int i = 0; i < 10000000; i++){ __NOP(); }
  USBLIB_Init();
	usb_on;
	for (int i = 0; i < 10000000; i++){ __NOP(); }
}
//////////////////////////////////////////////////////////////
struct usb_tx {
	char *str_tx;
	volatile uint16_t size_str_tx;
	volatile uint16_t size_str;
	volatile uint8_t number_sms;
	volatile _Bool busy_tx;//флаг события передачи - передается
	volatile _Bool ready_tx;
}usb_tx ={0,0,0,0,0,0};
//////////////////////////////////////////////////////////////
struct usb_rx {
	char *str_rx;
	volatile uint16_t size_str_rx;
	volatile _Bool ready_rx;
	volatile _Bool rewrite_rx;
}usb_rx ={0,0,0,0};
//////////////////////////////////////////////////////////////
void SysTick_Handler(void)
{
	if( ( usb_tx.busy_tx == 1 ) && ( usb_tx.ready_tx == 1 ) )
    {
    	/*попали сюда через 1 мСек значит передача завершена*/
    	usb_tx.busy_tx = 0;
    	usb_tx.ready_tx = 0;
    	/*обнулить строку передачи*/
    	usb_tx.str_tx = memset( usb_tx.str_tx, NULL, usb_tx.size_str_tx );
    	usb_tx.size_str = 0;
    	usb_tx.size_str_tx = 0;
    }
	if( ( usb_tx.ready_tx == 1 ) && ( usb_tx.busy_tx == 0 ) )
    {
    	usb_tx.size_str_tx = strlen( usb_tx.str_tx );
    	if( _LineState.L ){USBLIB_Transmit((uint16_t *)usb_tx.str_tx, (uint16_t)usb_tx.size_str_tx);}
    	usb_tx.busy_tx = 1;
    }
}
int usb_sms( char * str )
{
	if( usb_tx.busy_tx == 1 ){ return 1; }/*занято передачей*/
	usb_tx.size_str = strlen( str ) + 6 ;/*размер строки сообщения*/
	if( ( usb_tx.size_str ) > CDC_DATA_FS_MAX_PACKET_SIZE ){ return -1;}/*ошибка размер сообщения слишком большой*/
	usb_tx.size_str_tx = strlen( usb_tx.str_tx );/*размер строки передачи*/
	if( ( usb_tx.size_str + usb_tx.size_str_tx ) > CDC_DATA_FS_MAX_PACKET_SIZE ){ return 2;}/*ждите освождения не лезет*/
	else
    { /* прибавить к строке передачи новое сообщение. поднять флаг готовности данных*/
    	memmove( ( usb_tx.str_tx + usb_tx.size_str_tx ), str , usb_tx.size_str );
    	usb_tx.ready_tx = 1;
    	return 0;
    }
}
int init_pwm( uint16_t f_pwm, uint16_t dt1, uint16_t dt2, uint16_t dt3 )
{
	/*Таймер 1, режим ШИМ на три канала
	1 - PA8(CH1)
	2 - PA9(CH2)
	3 - PA10(CH3)*/
  GPIOA->CRH = ( GPIOA->CRH & ~( 
	GPIO_CRH_MODE8 | GPIO_CRH_CNF8 | /*канал 1*/
	GPIO_CRH_MODE9 | GPIO_CRH_CNF9 | /*канал 2*/
	GPIO_CRH_MODE10 | GPIO_CRH_CNF10 /*канал 3*/
	) ) | 
	GPIO_CRH_CNF8_0 | GPIO_CRH_MODE8_1 | GPIO_CRH_MODE8_0 |  /*канал 1 ВЫХОД 50МГЦ АЛЬТ.ФУНКЦИЯ PUSH-PULL*/
	GPIO_CRH_CNF9_0 | GPIO_CRH_MODE9_1 | GPIO_CRH_MODE9_0 |  /*канал 2 ВЫХОД 50МГЦ АЛЬТ.ФУНКЦИЯ PUSH-PULL*/
	GPIO_CRH_CNF10_0 | GPIO_CRH_MODE10_1 | GPIO_CRH_MODE10_0 /*канал 3 ВЫХОД 50МГЦ АЛЬТ.ФУНКЦИЯ PUSH-PULL*/
	;	
	// ШИМ 10кГц
	/* F_CPU/72/f_pwm */
	uint16_t f = (F_CPU/72)/f_pwm;
	TIM1->PSC = 72-1;
  TIM1->ARR = f;
	//коэф. заполнения
	TIM1->CCR1 = dt1;
	TIM1->CCR2 = dt2;
	TIM1->CCR3 = dt3;
	TIM1->CCER |= TIM_CCER_CC1E; /*канал 1*/
	TIM1->CCER |= TIM_CCER_CC2E;/*канал 2*/
	TIM1->CCER |= TIM_CCER_CC3E;/*канал 3*/
	TIM1->BDTR |= TIM_BDTR_MOE;
  TIM1->CCMR1 = TIM_CCMR1_OC1M_2 | TIM_CCMR1_OC1M_1;/*канал 1*/
	TIM1->CCMR1 = TIM_CCMR1_OC2M_2 | TIM_CCMR1_OC2M_1;/*канал 2*/
	TIM1->CCMR2 = TIM_CCMR2_OC3M_2 | TIM_CCMR2_OC3M_1;/*канал 3*/
	TIM1->CR1 &= ~TIM_CR1_DIR;
	TIM1->CR1 &= ~TIM_CR1_CMS;
	TIM1->CR1 |= TIM_CR1_CEN;
	return 0;
}
void set_null_pos( void )
{
	while( usb_sms( "set null-run\r\n" ) != 0 ){};
    /*функция установки нуля по всем осям*/
	while( usb_sms( "set null-done\r\n" ) != 0 ){};
    /*готовность к дальнейшей работе*/
	while( usb_sms( "ready to receive commands\r\n" ) != 0 ){};
}
void x_goto(void)
{
	char *str1 = strtok( NULL, "/=%");
	float num =	atof( str1 );
	/* движение оси х до точки num */
	while( usb_sms( "x axis set to " ) != 0 ){};
	while( usb_sms( str1 ) != 0 ){};
	while( usb_sms( "mm. run\r\n" ) != 0 ){};
	/*выполнили*/
	while( usb_sms( "x axis completed\r\n" ) != 0 ){};
}
void sms_rx( void )
{
	if( usb_rx.ready_rx )
    {
    	char *axis = strtok( usb_rx.str_rx, "/=%" );	 
    	if( ( strcmp( "x", axis ) == 0 ) ){ x_goto(); goto NOTERROR; }
    	if( ( strcmp( "y", axis ) == 0 ) ){while( usb_sms( "axis y\r\n" ) != 0 ){}; goto NOTERROR;}
    	if( ( strcmp( "z", axis ) == 0 ) ){while( usb_sms( "axis z\r\n" ) != 0 ){}; goto NOTERROR;}
    	if( ( strcmp( "xyz", axis ) == 0 ) ){while( usb_sms( "axis xyz\r\n" ) != 0 ){}; goto NOTERROR;}
    	if( ( strcmp( "setup", axis ) == 0 ) ){while( usb_sms( "setup\r\n" ) != 0 ){}; goto NOTERROR;}
    	if( ( strcmp( "stop", axis ) == 0 ) ){while( usb_sms( "stop\r\n" ) != 0 ){}; goto NOTERROR;}
    	while( usb_sms( "erroneous command\r\n" ) != 0 );
    	NOTERROR:    
    	usb_rx.size_str_rx = strlen( usb_rx.str_rx );
    	memset( usb_rx.str_rx, NULL, usb_rx.size_str_rx );
    	usb_rx.ready_rx = 0;
    }
}
int main(void)
{
	clk_init();
	usb_pin_usb_init();
	led_usb_off;
	SysTick_Config(TimerTick);
	usb_tx.str_tx = calloc( CDC_DATA_FS_MAX_PACKET_SIZE, sizeof( char ) );
	usb_rx.str_rx = calloc( CDC_DATA_FS_MAX_PACKET_SIZE, sizeof( char ) );
	set_null_pos();
	while( 1 )
    {
    	sms_rx();
    }
}
void uUSBLIB_DataReceivedHandler( uint16_t *Data, uint16_t Length )
{
	usb_rx.size_str_rx = strlen( usb_rx.str_rx );
	if( ( usb_rx.size_str_rx + Length ) <= CDC_DATA_FS_MAX_PACKET_SIZE )
    { 
    	memmove( ( usb_rx.str_rx + usb_rx.size_str_rx ), (char*)Data , Length );
    	usb_rx.ready_rx = 1;
    }
	else
    {
    	memset( usb_rx.str_rx, NULL, usb_rx.size_str_rx );
    	memmove( usb_rx.str_rx , (char*)Data , Length );
    	usb_rx.ready_rx = 1;
    	usb_rx.rewrite_rx = 1;
    }
}
void uUSBLIB_LineStateHandler( USBLIB_WByte LineState )
{
    if (LineState.L) 
    	{      
        _LineState = LineState;
    	}
}

http://s8.uploads.ru/t/WtNmi.png
вроде что-то вменяемое начинает получаться.

5

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

6

Код:
#include "stm32f10x.h"
#include "usblib.h"
#include "string.h"
#include <stdio.h>
#include <stdlib.h>

#define led_usb_on    	(GPIOC->BSRR = GPIO_BSRR_BR13)
#define led_usb_off    	(GPIOC->BSRR = GPIO_BSRR_BS13)
#define usb_on        	(GPIOB->BSRR = GPIO_BSRR_BS13)
#define usb_off        	(GPIOB->BSRR = GPIO_BSRR_BR13)
#define left_on     (GPIOB->BSRR = GPIO_BSRR_BS7)
#define left_off     (GPIOB->BSRR = GPIO_BSRR_BR7)
#define right_on 	(GPIOB->BSRR = GPIO_BSRR_BS8)
#define right_off	(GPIOB->BSRR = GPIO_BSRR_BR8)
#define driver_on         (GPIOB->BSRR = GPIO_BSRR_BS9)
#define driver_off	     (GPIOB->BSRR = GPIO_BSRR_BR9)
/*системный таймер, прерывание каждую мСек */
#define F_CPU     72000000UL	// Тактовая у нас 72МГЦ
#define TimerTick  	F_CPU/1000	// Нам нужен килогерц

USBLIB_WByte _LineState;

struct usb_tx {
	char *str_tx;
	volatile uint16_t size_str_tx;
	volatile uint16_t size_str;
	volatile uint8_t number_sms;
	volatile _Bool busy_tx;
	volatile _Bool ready_tx;
}usb_tx ={0,0,0,0,0,0};

struct usb_rx {
	char *str_rx;
	volatile uint16_t size_str_rx;
	volatile _Bool ready_rx;
	volatile _Bool rewrite_rx;
}usb_rx ={0,0,0,0};

struct axis_x {
	volatile _Bool run;
	volatile float pos;
} axis_x = { 0, 0 };

void clk_init( void )/*клок и включение периферии*/
{
	RCC->CFGR &= ~RCC_CFGR_SW; // Change System Clock to HSI
  while ((RCC->CFGR & RCC_CFGR_SWS) != 0x00){ __NOP(); }
  RCC->CR &= ~RCC_CR_PLLON; // Disable Pll
  while ((RCC->CR & RCC_CR_PLLON)){ __NOP(); }
  RCC->CFGR &= ~0x3C0000;
  RCC->CFGR |= RCC_CFGR_PLLMULL9; // 6
/*тута можно поиграться чтоб на усб 48 МГц а клок 72МГц*/
//RCC->CFGR |= RCC_CFGR_USBPRE;
  RCC->CFGR |= RCC_CFGR_PLLSRC;
  RCC->CR |= RCC_CR_PLLON;
  while (!(RCC->CR & RCC_CR_PLLON)){ __NOP(); }
  RCC->CFGR |= RCC_CFGR_SW_1; // Change System Clock to PLL
  while ((RCC->CFGR & RCC_CFGR_SWS) != RCC_CFGR_SWS_1){ __NOP(); }
  RCC->APB2ENR |= RCC_APB2ENR_IOPAEN | RCC_APB2ENR_IOPBEN | RCC_APB2ENR_IOPCEN | RCC_APB2ENR_AFIOEN | RCC_APB2ENR_TIM1EN;
	RCC->APB1ENR |= RCC_APB1ENR_TIM2EN;
}

void usb_pin_usb_init(void)
{
/* ========= PB13 USB CONNECT ========= */
/* PC13 - LED. Output PP */
	GPIOC->CRH |= GPIO_CRH_MODE13_0;
  GPIOC->CRH &= ~GPIO_CRH_CNF13;
/* PA15 - USB EN. Output PP */
  GPIOB->CRH |= GPIO_CRH_MODE13_0;
  GPIOB->CRH &= ~GPIO_CRH_CNF13;
	usb_off;
  for (int i = 0; i < 10000000; i++){ __NOP(); }
  USBLIB_Init();
	usb_on;
	for (int i = 0; i < 10000000; i++){ __NOP(); }
}

void SysTick_Handler(void)
{
	if( ( usb_tx.busy_tx == 1 ) && ( usb_tx.ready_tx == 1 ) )//попали сюда через 1 мСек значит передача завершена
    {
    	usb_tx.busy_tx = 0;
    	usb_tx.ready_tx = 0;
    	//обнулить строку передачи
    	usb_tx.str_tx = memset( usb_tx.str_tx, NULL, usb_tx.size_str_tx );
    	usb_tx.size_str = 0;
    	usb_tx.size_str_tx = 0;
    }
	if( ( usb_tx.ready_tx == 1 ) && ( usb_tx.busy_tx == 0 ) )
    {
    	usb_tx.size_str_tx = strlen( usb_tx.str_tx );
    	if( _LineState.L )
        {
        	USBLIB_Transmit((uint16_t *)usb_tx.str_tx, (uint16_t)usb_tx.size_str_tx);
        }
    	usb_tx.busy_tx = 1;
    }
}

int usb_sms( char * str )
{
	if( usb_tx.busy_tx == 1 )//занято передачей
    { 
    	return 1; 
    }
	usb_tx.size_str = strlen( str ) + 6 ;//размер строки сообщения
	if( ( usb_tx.size_str ) > CDC_DATA_FS_MAX_PACKET_SIZE )//ошибка размер сообщения слишком большой
    { 
    	return -1;
    }
	usb_tx.size_str_tx = strlen( usb_tx.str_tx );//размер строки передачи
	if( ( usb_tx.size_str + usb_tx.size_str_tx ) > CDC_DATA_FS_MAX_PACKET_SIZE )//ждите освождения не лезет
    { 
    	return 2;
    }
	else// прибавить к строке передачи новое сообщение. поднять флаг готовности данных
    { 
    	memmove( ( usb_tx.str_tx + usb_tx.size_str_tx ), str , usb_tx.size_str );
    	usb_tx.ready_tx = 1;
    	return 0;
    }
}

void set_null_pos( void )
{
	while( usb_sms( "set null-run\r\n" ) != 0 ){};
    /*функция установки нуля по всем осям*/
	while( usb_sms( "set null-done\r\n" ) != 0 ){};
    /*готовность к дальнейшей работе*/
	while( usb_sms( "ready to receive commands\r\n" ) != 0 ){};
}

void move_x( void )
{
	if( axis_x.run == 1 )//надо выполнить
    {
    	while( usb_sms( "started x\r\n" ) != 0 );//передаем начали выполнять
    	//выполнение
    	//......
    	//выполнили
    	while( usb_sms( "finished x\r\n" ) != 0 );//передаем выполнили
    	axis_x.run = 0;
    }
}	
int main(void)
{
	clk_init();
	usb_pin_usb_init();
	led_usb_off;
	SysTick_Config(TimerTick);
	usb_tx.str_tx = calloc( CDC_DATA_FS_MAX_PACKET_SIZE, sizeof( char ) );
	usb_rx.str_rx = calloc( CDC_DATA_FS_MAX_PACKET_SIZE, sizeof( char ) );
	set_null_pos();
	while( 1 )
    {
    	move_x();
    }
}
void uUSBLIB_DataReceivedHandler( uint16_t *Data, uint16_t Length )
{
	memmove( usb_rx.str_rx , (char*)Data , Length );//перемещаем в буфер
	char *str1 = strtok( usb_rx.str_rx, "/" );//забираем строку обращения к оси или команды
	if( ( strcmp( "x", str1 ) == 0 ) )//обращение к оси x
    {
    	axis_x.run = 1;//подымаем флаг для оси x
    	str1 = strtok( NULL, "/=%");//забираем строку данных
    	axis_x.pos =	atof( str1 );//переводим сторку данных в переменную
    	while( usb_sms( "accepted x\r\n" ) != 0 );//передаем принято
    	memset( usb_rx.str_rx, NULL, Length );//обнуляем буфер
    }
    else//не известно к какой оси обратились или неизвестная команда
    	{
        while( usb_sms( "erroneous command\r\n" ) != 0 );//передаем не распознано
    	}
}
void uUSBLIB_LineStateHandler( USBLIB_WByte LineState )
{
    if (LineState.L) 
    	{
        _LineState = LineState;
    	}
}

7

Код:
#include "stm32f10x.h"
#include "usblib.h"
#include "string.h"
#include <stdio.h>
#include <stdlib.h>

#define led_usb_on    	(GPIOC->BSRR = GPIO_BSRR_BR13)
#define led_usb_off    	(GPIOC->BSRR = GPIO_BSRR_BS13)
#define usb_on        	(GPIOB->BSRR = GPIO_BSRR_BS13)
#define usb_off        	(GPIOB->BSRR = GPIO_BSRR_BR13)
#define left_on     (GPIOB->BSRR = GPIO_BSRR_BS7)
#define left_off     (GPIOB->BSRR = GPIO_BSRR_BR7)
#define right_on 	(GPIOB->BSRR = GPIO_BSRR_BS8)
#define right_off	(GPIOB->BSRR = GPIO_BSRR_BR8)
#define driver_on         (GPIOB->BSRR = GPIO_BSRR_BS9)
#define driver_off	     (GPIOB->BSRR = GPIO_BSRR_BR9)
/*системный таймер, прерывание каждую мСек */
#define F_CPU     72000000UL	// Тактовая у нас 72МГЦ
#define TimerTick  	F_CPU/1000	// Нам нужен килогерц

USBLIB_WByte _LineState;

struct usb_tx {
	char *str_tx;
	volatile uint16_t size_str_tx;
	volatile uint16_t size_str;
	volatile uint8_t number_sms;
	volatile _Bool busy_tx;
	volatile _Bool ready_tx;
}usb_tx ={0,0,0,0,0,0};

struct axis_x {
	volatile _Bool run;
	volatile float pos;
} axis_x = { 0, 0 };

void clk_init( void )/*клок и включение периферии*/
{
	RCC->CFGR &= ~RCC_CFGR_SW; // Change System Clock to HSI
  while ((RCC->CFGR & RCC_CFGR_SWS) != 0x00){ __NOP(); }
  RCC->CR &= ~RCC_CR_PLLON; // Disable Pll
  while ((RCC->CR & RCC_CR_PLLON)){ __NOP(); }
  RCC->CFGR &= ~0x3C0000;
  RCC->CFGR |= RCC_CFGR_PLLMULL9; // 6
/*тута можно поиграться чтоб на усб 48 МГц а клок 72МГц*/
//RCC->CFGR |= RCC_CFGR_USBPRE;
  RCC->CFGR |= RCC_CFGR_PLLSRC;
  RCC->CR |= RCC_CR_PLLON;
  while (!(RCC->CR & RCC_CR_PLLON)){ __NOP(); }
  RCC->CFGR |= RCC_CFGR_SW_1; // Change System Clock to PLL
  while ((RCC->CFGR & RCC_CFGR_SWS) != RCC_CFGR_SWS_1){ __NOP(); }
  RCC->APB2ENR |= RCC_APB2ENR_IOPAEN | RCC_APB2ENR_IOPBEN | RCC_APB2ENR_IOPCEN | RCC_APB2ENR_AFIOEN | RCC_APB2ENR_TIM1EN;
	RCC->APB1ENR |= RCC_APB1ENR_TIM2EN;
}

void usb_pin_usb_init(void)
{
/* ========= PB13 USB CONNECT ========= */
/* PC13 - LED. Output PP */
	GPIOC->CRH |= GPIO_CRH_MODE13_0;
  GPIOC->CRH &= ~GPIO_CRH_CNF13;
/* PA15 - USB EN. Output PP */
  GPIOB->CRH |= GPIO_CRH_MODE13_0;
  GPIOB->CRH &= ~GPIO_CRH_CNF13;
	usb_off;
  for (int i = 0; i < 10000000; i++){ __NOP(); }
  USBLIB_Init();
	usb_on;
	for (int i = 0; i < 10000000; i++){ __NOP(); }
}

void SysTick_Handler(void)
{
	if( ( usb_tx.busy_tx == 1 ) && ( usb_tx.ready_tx == 1 ) )//попали сюда через 1 мСек значит передача завершена
    {
    	usb_tx.busy_tx = 0;
    	usb_tx.ready_tx = 0;
    	//обнулить строку передачи
    	usb_tx.str_tx = memset( usb_tx.str_tx, NULL, usb_tx.size_str_tx );
    	usb_tx.size_str = 0;
    	usb_tx.size_str_tx = 0;
    }
	if( ( usb_tx.ready_tx == 1 ) && ( usb_tx.busy_tx == 0 ) )
    {
    	usb_tx.size_str_tx = strlen( usb_tx.str_tx );
    	if( _LineState.L )
        {
        	USBLIB_Transmit((uint16_t *)usb_tx.str_tx, (uint16_t)usb_tx.size_str_tx);
        }
    	usb_tx.busy_tx = 1;
    }
}

int usb_sms( char * str )
{
	if( usb_tx.busy_tx == 1 )//занято передачей
    { 
    	return 1; 
    }
	usb_tx.size_str = strlen( str ) + 6 ;//размер строки сообщения
	if( ( usb_tx.size_str ) > CDC_DATA_FS_MAX_PACKET_SIZE )//ошибка размер сообщения слишком большой
    { 
    	return -1;
    }
	usb_tx.size_str_tx = strlen( usb_tx.str_tx );//размер строки передачи
	if( ( usb_tx.size_str + usb_tx.size_str_tx ) > CDC_DATA_FS_MAX_PACKET_SIZE )//ждите освождения не лезет
    { 
    	return 2;
    }
	else// прибавить к строке передачи новое сообщение. поднять флаг готовности данных
    { 
    	memmove( ( usb_tx.str_tx + usb_tx.size_str_tx ), str , usb_tx.size_str );
    	usb_tx.ready_tx = 1;
    	return 0;
    }
}

void set_null_pos( void )
{
	while( usb_sms( "set null-run\r\n" ) != 0 ){};
    /*функция установки нуля по всем осям*/
	while( usb_sms( "set null-done\r\n" ) != 0 ){};
    /*готовность к дальнейшей работе*/
	while( usb_sms( "ready to receive commands\r\n" ) != 0 ){};
}

void move_x( void )
{
	if( axis_x.run == 1 )//надо выполнить
    {
    	while( usb_sms( "started x\r\n" ) != 0 );//передаем начали выполнять
    	//выполнение
    	//......
    	//выполнили
    	while( usb_sms( "finished x\r\n" ) != 0 );//передаем выполнили
    	axis_x.run = 0;
    }
}	
int main(void)
{
	clk_init();
	usb_pin_usb_init();
	led_usb_off;
	SysTick_Config(TimerTick);
	usb_tx.str_tx = calloc( CDC_DATA_FS_MAX_PACKET_SIZE, sizeof( char ) );
	set_null_pos();
	while( 1 )
    {
    	move_x();
    }
}
void uUSBLIB_DataReceivedHandler( uint16_t *Data, uint16_t Length )
{
	char *str1 = strtok( ( char *)Data, "/" );//забираем строку обращения к оси или команды
	if( ( strcmp( "x", str1 ) == 0 ) )//обращение к оси x
    {
    	axis_x.run = 1;//подымаем флаг для оси x
    	str1 = strtok( NULL, "/=%");//забираем строку данных
    	axis_x.pos =	atof( str1 );//переводим сторку данных в переменную
    	while( usb_sms( "accepted x\r\n" ) != 0 );//передаем принято
    }
    else//не известно к какой оси обратились или неизвестная команда
    	{
        while( usb_sms( "erroneous command\r\n" ) != 0 );//передаем не распознано
    	}
}
void uUSBLIB_LineStateHandler( USBLIB_WByte LineState )
{
    if (LineState.L) 
    	{
        _LineState = LineState;
    	}
}

8

Код:
void uUSBLIB_DataReceivedHandler( uint16_t *Data, uint16_t Length )
{
	// move/100/10/1/ или pwm/50%0%0%
	memmove( buf_rx , (char*)Data , Length );//перемещаем в буфер
	char *str1 = strstr( buf_rx, "move" );
	char *str2 = strstr( buf_rx, "pwm" );
	if( str1 != 0 ){
    while( usb_sms( "accepted move\r\n" ) != 0 );
    strtok( str1, "/");//забираем строку данных
    str1 = strtok( NULL, "/");//забираем строку данных
    axis.x_pos =	atof( str1 );//отладка
    while( usb_sms( str1 ) != 0 );
	}
	else if( str2 != 0 ){
    while( usb_sms( "accepted pwm\r\n" ) != 0 );
	}
	else if( ( str1 == 0 ) && ( str2 == 0 )){
    while( usb_sms( "erroneous command\r\n" ) != 0 );
	}
	memset( buf_rx, NULL, Length );
}

9

замена #define CDC_DATA_FS_MAX_PACKET_SIZE 64 на #define CDC_DATA_FS_MAX_PACKET_SIZE 255

Не будет же работать, если только не вмешаться в исходники "usb_lib": там отправляется весь буфер за один присест, а он не может быть больше 64 байт, т.к. это CDC.

10

Eddy_Em написал(а):

Не будет же работать, если только не вмешаться в исходники "usb_lib": там отправляется весь буфер за один присест, а он не может быть больше 64 байт, т.к. это CDC.

я не буду ничего утверждать, но я проверял, когда настраивал передачу, вводил отдельную переменную "номер отравления" а сообщение наполнял счетом "01234...10011002" без разделения. при CDC_DATA_FS_MAX_PACKET_SIZE 255 передавалось ровно 255 символов(не сообщение заканчивалось на 255, а тупо пересчитывал  :blush: ) в одном отравлении, при 64 - 64. но мог и начудить чего...
тут как бэ автора спросить надо. мне в глубины лезть сейчас чревато, зависанием еще на месяц другой.
за намек спасибо, будут грабли буду иметь в виду.
хотя почитал про Bulk Data Transfers http://usb.fober.net/teoriya/Tipy-peredachi-dannyx/ вы правы, не должно работать. но ведь... как то работало... ничего не понимаю...
на этом этапе проще будет не гнаться за длинной посылки. короче подкорректирую, чтобы себя, и может быть еще кого, не вводить в заблуждение.

11

Код:
#include "stm32f10x.h"
#include "usblib.h"
#include "string.h"
#include <stdio.h>
#include <stdlib.h>

#define led_usb_on    	(GPIOC->BSRR = GPIO_BSRR_BR13)
#define led_usb_off    	(GPIOC->BSRR = GPIO_BSRR_BS13)
#define usb_on        	(GPIOB->BSRR = GPIO_BSRR_BS13)
#define usb_off        	(GPIOB->BSRR = GPIO_BSRR_BR13)
#define left_on     (GPIOB->BSRR = GPIO_BSRR_BS7)
#define left_off     (GPIOB->BSRR = GPIO_BSRR_BR7)
#define right_on 	(GPIOB->BSRR = GPIO_BSRR_BS8)
#define right_off	(GPIOB->BSRR = GPIO_BSRR_BR8)
#define driver_on         (GPIOB->BSRR = GPIO_BSRR_BS9)
#define driver_off	     (GPIOB->BSRR = GPIO_BSRR_BR9)
/*системный таймер, прерывание каждую мСек */
#define F_CPU     72000000UL	// Тактовая у нас 72МГЦ
#define TimerTick  	F_CPU/1000	// Нам нужен килогерц

USBLIB_WByte _LineState;
char *buf_rx = 0;

struct usb_tx {
	char *str_tx;
	volatile uint16_t size_str_tx;
	volatile uint16_t size_str;
	volatile uint8_t number_sms;
	volatile _Bool busy_tx;
	volatile _Bool ready_tx;
}usb_tx ={0,0,0,0,0,0};

struct axis {
	volatile _Bool pos_change;
	volatile _Bool pwm_change;
	volatile _Bool stop;
	volatile _Bool run;
	volatile float pos_x;
	volatile float pos_y;
	volatile float pos_z;
	volatile uint16_t pwm_x;
	volatile uint16_t pwm_y;
	volatile uint16_t pwm_z;	
} axis = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };

void clk_init( void )/*клок и включение периферии*/
{
	RCC->CFGR &= ~RCC_CFGR_SW; // Change System Clock to HSI
  while ((RCC->CFGR & RCC_CFGR_SWS) != 0x00){ __NOP(); }
  RCC->CR &= ~RCC_CR_PLLON; // Disable Pll
  while ((RCC->CR & RCC_CR_PLLON)){ __NOP(); }
  RCC->CFGR &= ~0x3C0000;
  RCC->CFGR |= RCC_CFGR_PLLMULL9; // 6
/*тута можно поиграться чтоб на усб 48 МГц а клок 72МГц*/
//RCC->CFGR |= RCC_CFGR_USBPRE;
  RCC->CFGR |= RCC_CFGR_PLLSRC;
  RCC->CR |= RCC_CR_PLLON;
  while (!(RCC->CR & RCC_CR_PLLON)){ __NOP(); }
  RCC->CFGR |= RCC_CFGR_SW_1; // Change System Clock to PLL
  while ((RCC->CFGR & RCC_CFGR_SWS) != RCC_CFGR_SWS_1){ __NOP(); }
  RCC->APB2ENR |= RCC_APB2ENR_IOPAEN | RCC_APB2ENR_IOPBEN | RCC_APB2ENR_IOPCEN | RCC_APB2ENR_AFIOEN | RCC_APB2ENR_TIM1EN;
	RCC->APB1ENR |= RCC_APB1ENR_TIM2EN;
}

void usb_pin_usb_init(void)
{
/* ========= PB13 USB CONNECT ========= */
/* PC13 - LED. Output PP */
	GPIOC->CRH |= GPIO_CRH_MODE13_0;
  GPIOC->CRH &= ~GPIO_CRH_CNF13;
/* PA15 - USB EN. Output PP */
  GPIOB->CRH |= GPIO_CRH_MODE13_0;
  GPIOB->CRH &= ~GPIO_CRH_CNF13;
	usb_off;
  for (int i = 0; i < 10000000; i++){ __NOP(); }
  USBLIB_Init();
	usb_on;
	for (int i = 0; i < 10000000; i++){ __NOP(); }
}

int usb_sms( char * str )
{
	if( usb_tx.busy_tx == 1 )//занято передачей
    { 
    	return 1; 
    }
	usb_tx.size_str = strlen( str ) + 6 ;//размер строки сообщения
	if( ( usb_tx.size_str ) > CDC_DATA_FS_MAX_PACKET_SIZE )//ошибка размер сообщения слишком большой
    { 
    	return -1;
    }
	usb_tx.size_str_tx = strlen( usb_tx.str_tx );//размер строки передачи
	if( ( usb_tx.size_str + usb_tx.size_str_tx ) > CDC_DATA_FS_MAX_PACKET_SIZE )//ждите освождения не лезет
    { 
    	return 2;
    }
	else// прибавить к строке передачи новое сообщение. поднять флаг готовности данных
    { 
    	memmove( ( usb_tx.str_tx + usb_tx.size_str_tx ), str , usb_tx.size_str );
    	usb_tx.ready_tx = 1;
    	return 0;
    }
}

void set_null_pos( void )
{
	while( usb_sms( "set null-run\r\n" ) != 0 ){};
    /*функция установки нуля по всем осям*/
	while( usb_sms( "set null-done\r\n" ) != 0 ){};
    /*готовность к дальнейшей работе*/
	while( usb_sms( "ready to receive commands\r\n" ) != 0 ){};
}

void comm( void )
{
	if( axis.pos_change == 1 )//надо выполнить
    {
    	while( usb_sms( "started move\r\n" ) != 0 );//передаем начали выполнять
    	//выполнение
    	//......
    	//выполнили
    	while( usb_sms( "finished move\r\n" ) != 0 );//передаем выполнили
    	axis.pos_change = 0;
    }
	if( axis.pwm_change == 1 )//надо выполнить
    {
    	while( usb_sms( "started pwm change\r\n" ) != 0 );//передаем начали выполнять
    	//выполнение
    	//......
    	//выполнили
    	while( usb_sms( "finished pwm change\r\n" ) != 0 );//передаем выполнили
    	axis.pwm_change = 0;
    }
}	
int main(void)
{
	clk_init();
	usb_pin_usb_init();
	led_usb_off;
	SysTick_Config(TimerTick);
	usb_tx.str_tx = calloc( CDC_DATA_FS_MAX_PACKET_SIZE, sizeof( char ) );
	set_null_pos();
	while( 1 )
    {
    	comm();
    }
}
void uUSBLIB_DataReceivedHandler( uint16_t *Data, uint16_t Length )
{
	char *buf = (char*)Data + ( uint8_t)Length;//указатель на окончание данных
	*buf = NULL;//зануляем
	buf = (char*)Data ;//работаем как со строкой
	char *str1 = strstr( buf, "move" );
	char *str2 = strstr( buf, "pwm" );
	char *str3 = strstr( buf, "stop" );//выкл драйвер
	char *str4 = strstr( buf, "run" );//вкл драйвер
	if( str1 != 0 )
    {
    	while( usb_sms( "accepted move\r\n" ) != 0 );    
    	strtok( str1, "/");//пропускаем название команды
    
    	str1 = strtok( NULL, "/");//забираем строку данных
    	axis.pos_x =	atof( str1 );
    
    	while( usb_sms( str1 ) != 0 );//отладка
    	while( usb_sms( "/" ) != 0 );
    
    	str1 = strtok( NULL, "/");//забираем строку данных
    	axis.pos_y =	atof( str1 );
    
    	while( usb_sms( str1 ) != 0 );//отладка
    	while( usb_sms( "/" ) != 0 );
    
    	str1 = strtok( NULL, "/");//забираем строку данных
    	axis.pos_z =	atof( str1 );
    
    	while( usb_sms( str1 ) != 0 );//отладка
    	while( usb_sms( "\r\n" ) != 0 );

    	axis.pos_change = 1;
    }
	else if( str2 != 0 )
    {
    	while( usb_sms( "accepted pwm\r\n" ) != 0 );
    	strtok( str2, "/");//пропускаем название команды
    
    	str2 = strtok( NULL, "/");//забираем строку данных
    	axis.pwm_x =	atof( str2 );
    
    	while( usb_sms( str2 ) != 0 );//отладка
    	while( usb_sms( "/" ) != 0 );
    
    	str2 = strtok( NULL, "/");//забираем строку данных
    	axis.pwm_y =	atof( str2 );
    
    	while( usb_sms( str2 ) != 0 );//отладка
    	while( usb_sms( "/" ) != 0 );
    
    	str2 = strtok( NULL, "/");//забираем строку данных
    	axis.pwm_z =	atof( str2 );
    
    	while( usb_sms( str2 ) != 0 );//отладка
    	while( usb_sms( "\r\n" ) != 0 );
    	
    	axis.pwm_change = 1;
    }
	else if( str3 != 0 )
    {
    	while( usb_sms( "driver disabled\r\n" ) != 0 );    	
    	axis.stop = 1;
    }
	else if( str4 != 0 )
    {
    	while( usb_sms( "driver enabled\r\n" ) != 0 );    	
    	axis.stop = 0;
    }
	else if( ( str1 == 0 ) && ( str2 == 0 ) && ( str3 == 0 ) && ( str4 == 0 ) ){
    while( usb_sms( "erroneous command\r\n" ) != 0 );
	}
}
void uUSBLIB_LineStateHandler( USBLIB_WByte LineState )
{
    if (LineState.L) 
    	{
        _LineState = LineState;
    	}
}

void SysTick_Handler(void)
{
	if( ( usb_tx.busy_tx == 1 ) && ( usb_tx.ready_tx == 1 ) )//попали сюда через 1 мСек значит передача завершена
    {
    	usb_tx.busy_tx = 0;
    	usb_tx.ready_tx = 0;
    	//обнулить строку передачи
    	usb_tx.str_tx = memset( usb_tx.str_tx, NULL, usb_tx.size_str_tx );
    	usb_tx.size_str = 0;
    	usb_tx.size_str_tx = 0;
    }
	if( ( usb_tx.ready_tx == 1 ) && ( usb_tx.busy_tx == 0 ) )
    {
    	usb_tx.size_str_tx = strlen( usb_tx.str_tx );
    	if( _LineState.L )
        {
        	USBLIB_Transmit((uint16_t *)usb_tx.str_tx, (uint16_t)usb_tx.size_str_tx);
        }
    	usb_tx.busy_tx = 1;
    }
}

12

Код:
RCC->APB2ENR |= RCC_APB2ENR_IOPBEN | RCC_APB2ENR_AFIOEN
AFIO->MAPR|=AFIO_MAPR_SWJ_CFG_JTAGDISABLE;
////////////////////////////////////////////////////////////////////////////////
///НАСТРОЙКА ПРЕРЫВАНИЯ ПО ИЗМЕНЕНИЮ УРОВНЯ H->L И L->H НА ПИНЕ B0 ///////////// 
  GPIOB->CRL = ( GPIOB->CRL & ~( GPIO_CRL_MODE0 | GPIO_CRL_CNF0 ) ) | GPIO_CRL_CNF0_1 ;	
	GPIOB->ODR |= GPIO_ODR_ODR0;
  AFIO->EXTICR[0] |= AFIO_EXTICR1_EXTI0_PB; //Настраиваем прерывания на ПИН B0
  EXTI->IMR |= EXTI_IMR_MR0; //Разрешаем прерывания с этой ноги
  EXTI->FTSR |= EXTI_FTSR_TR0; //по спаду сигнала	
	NVIC_EnableIRQ(EXTI0_IRQn);	
////////////////////////////////////////////////////////////////////////////////
///НАСТРОЙКА ПРЕРЫВАНИЯ ПО ИЗМЕНЕНИЮ УРОВНЯ H->L И L->H НА ПИНЕ B1 ///////////// 
  GPIOB->CRL = ( GPIOB->CRL & ~( GPIO_CRL_MODE1 | GPIO_CRL_CNF1 ) ) | GPIO_CRL_CNF1_1 ;	
	GPIOB->ODR |= GPIO_ODR_ODR1;
  AFIO->EXTICR[0] |= AFIO_EXTICR1_EXTI1_PB; //Настраиваем прерывания на ПИН B0
  EXTI->IMR |= EXTI_IMR_MR1; //Разрешаем прерывания с этой ноги
  EXTI->FTSR |= EXTI_FTSR_TR1; //по спаду сигнала	
	NVIC_EnableIRQ(EXTI1_IRQn);    
////////////////////////////////////////////////////////////////////////////////
///НАСТРОЙКА ПРЕРЫВАНИЯ ПО ИЗМЕНЕНИЮ УРОВНЯ H->L И L->H НА ПИНЕ B3 ///////////// 
  GPIOB->CRL = ( GPIOB->CRL & ~( GPIO_CRL_MODE3 | GPIO_CRL_CNF3 ) ) | GPIO_CRL_CNF3_1 ;	
	GPIOB->ODR |= GPIO_ODR_ODR3;
  AFIO->EXTICR[0] |= AFIO_EXTICR1_EXTI3_PB; //Настраиваем прерывания на ПИН B0
  EXTI->IMR |= EXTI_IMR_MR3; //Разрешаем прерывания с этой ноги
  EXTI->FTSR |= EXTI_FTSR_TR3; //по спаду сигнала	
	NVIC_EnableIRQ(EXTI3_IRQn);
////////////////////////////////////////////////////////////////////////////////
///НАСТРОЙКА ПРЕРЫВАНИЯ ПО ИЗМЕНЕНИЮ УРОВНЯ H->L И L->H НА ПИНЕ B3 ///////////// 
  GPIOB->CRL = ( GPIOB->CRL & ~( GPIO_CRL_MODE3 | GPIO_CRL_CNF4 ) ) | GPIO_CRL_CNF4_1 ;	
	GPIOB->ODR |= GPIO_ODR_ODR4;
  AFIO->EXTICR[1] |= AFIO_EXTICR2_EXTI4_PB; //Настраиваем прерывания на ПИН B0
  EXTI->IMR |= EXTI_IMR_MR4; //Разрешаем прерывания с этой ноги
  EXTI->FTSR |= EXTI_FTSR_TR4; //по спаду сигнала	
	NVIC_EnableIRQ(EXTI4_IRQn);
void EXTI0_IRQHandler(void)
{
	led_usb_on;
	EXTI->PR |= EXTI_PR_PR0;
}

void EXTI1_IRQHandler(void)
{
	led_usb_off;
	EXTI->PR |= EXTI_PR_PR1;
}

void EXTI3_IRQHandler(void)
{
	led_usb_on;
	EXTI->PR |= EXTI_PR_PR3;
}
void EXTI4_IRQHandler(void)
{
	led_usb_off;
	EXTI->PR |= EXTI_PR_PR4;
}

13

Код:
void init_exti(void)
{
//ПИНЫ PORTB0-5, КРОМЕ PORTB.2 НА ВХОД С ПОДТЯЖКОЙ К ПИТАНИЮ
	GPIOB->CRL = ( GPIOB->CRL & ~( GPIO_CRL_MODE0 | GPIO_CRL_CNF0 | 
	GPIO_CRL_MODE1 | GPIO_CRL_CNF1 | GPIO_CRL_MODE3 | GPIO_CRL_CNF3 | 
	GPIO_CRL_MODE4 | GPIO_CRL_CNF4 | GPIO_CRL_MODE5 | GPIO_CRL_CNF5 
	) ) | 
	GPIO_CRL_CNF0_1 | GPIO_CRL_CNF1_1 | GPIO_CRL_CNF3_1 | GPIO_CRL_CNF4_1 | GPIO_CRL_CNF5_1;
  GPIOB->ODR |= GPIO_ODR_ODR0 | GPIO_ODR_ODR1 | GPIO_ODR_ODR3 | GPIO_ODR_ODR4 | GPIO_ODR_ODR5;//ПОДТЯГИВАЕМ К ПИТАНИЮ
//ПИН PORTА.2 НА ВХОД С ПОДТЯЖКОЙ К ПИТАНИЮ
	GPIOA->CRL = ( GPIOB->CRL & ~( GPIO_CRL_MODE2 | GPIO_CRL_CNF2 ) ) | GPIO_CRL_CNF2_1 ;
	GPIOA->ODR |= GPIO_ODR_ODR2;//ПОДТЯГИВАЕМ К ПИТАНИЮ
	AFIO->EXTICR[0] |= AFIO_EXTICR1_EXTI0_PB | AFIO_EXTICR1_EXTI1_PB | AFIO_EXTICR1_EXTI2_PA | AFIO_EXTICR1_EXTI3_PB; //Настраиваем прерывания на ПИН B.0, B.1, B.3, А.2
	AFIO->EXTICR[1] |= AFIO_EXTICR2_EXTI4_PB | AFIO_EXTICR2_EXTI5_PB;//Настраиваем прерывания на ПИН B.4, B.5
	EXTI->IMR |= EXTI_IMR_MR0 | EXTI_IMR_MR1 | EXTI_IMR_MR2 | EXTI_IMR_MR3 | EXTI_IMR_MR4 | EXTI_IMR_MR5;//Разрешаем прерывания ПИН 0-5
	EXTI->FTSR |= EXTI_FTSR_TR0 | EXTI_FTSR_TR1 | EXTI_FTSR_TR2 | EXTI_FTSR_TR3 | EXTI_FTSR_TR4 | EXTI_FTSR_TR5;//ПРЕРЫВАНИЕ ПО СПАДУ СИГНАЛА H->L	
	NVIC_EnableIRQ(EXTI0_IRQn);	
	NVIC_EnableIRQ(EXTI1_IRQn); 	
	NVIC_EnableIRQ(EXTI2_IRQn);	
	NVIC_EnableIRQ(EXTI3_IRQn);
	NVIC_EnableIRQ(EXTI4_IRQn);
	NVIC_EnableIRQ(EXTI9_5_IRQn);
}
void EXTI0_IRQHandler(void)
{
	if( EXTI->PR & EXTI_PR_PR0)
    {
    	led_usb_off;
    	EXTI->PR |= EXTI_PR_PR0;
    }
}

void EXTI1_IRQHandler(void)
{
	if( EXTI->PR & EXTI_PR_PR1)
    {
    	led_usb_off;
    	EXTI->PR |= EXTI_PR_PR1;
    }
}

void EXTI2_IRQHandler(void)
{
	if( EXTI->PR & EXTI_PR_PR2)
    {
    	led_usb_off;
    	EXTI->PR |= EXTI_PR_PR2;
    }
}

void EXTI3_IRQHandler(void)
{
	if( EXTI->PR & EXTI_PR_PR3)
    {
    	led_usb_off;
    	EXTI->PR |= EXTI_PR_PR3;
    }
}
void EXTI4_IRQHandler(void)
{
	if( EXTI->PR & EXTI_PR_PR4)
    {
    	led_usb_off;
    	EXTI->PR |= EXTI_PR_PR4;
    }
}
void EXTI9_5_IRQHandler(void)
{
	if( EXTI->PR & EXTI_PR_PR5)
    {
    	led_usb_on;
    	EXTI->PR |= EXTI_PR_PR5;
    }
}

Вы здесь » Микроконтроллеры » RA » Blue pill, STM32F103, ШИМ, управляем ДПТ через USB CDC. VNH2SP30.