stm32单片机裸机调用百度语音识别接口和合成接口的部分代码实现,有意向的可以联系我 qq790861133

stm32单片机裸机调用百度语音识别接口和合成接口的部分代码实现,有意向的可以联系我 qq790861133 ---作者:阮丁远

 

先介绍个要用到的函数:lwip 下 WebClient或者说http cilent的实现:




int8_t WebClient(const char *url, const char *post, uint8_t **pageBuf,uint8_t is_upload_wav,uint32_t wav_len1)
{
  
	 uint32_t i;
	
  uint8_t server_addr[200];//这2个放在局部变量里,防止多线程冲突:
     uint8_t web_addr[1200];//有的tts的二次url编码后的请求长度很长,所以这个大点
 ip_addr_t server_ip;


 uint8_t ishttps;
   uint16_t start_char_i;
    uint16_t start_len1;
  uint32_t ret_lens;
	 err_t err ;
	
   uint32_t  j, k;
   uint32_t head_and_wav_len1;

    struct netconn *conn = NULL;
    struct netbuf *inBuf = NULL;
    struct pbuf *q;
    char *request = NULL;
    uint32_t recvPos = 0;
    uint8_t *recvBuf;
    err_t err_msg;




    while(wifi_88w8801_sta.ip_addr.addr == 0x00)
    {
        return HTTP_ROUTE_NOT_FOUND;
    }

	 
	 
   if(strncasecmp((const char *)url, "http://", 7) == 0||strncasecmp((const char *)url, "https://", 8) == 0) 		/* 只处理http协议 */
    {
		 
		 
		 if(strncasecmp((const char *)url, "http://", 7) == 0){
			 
			 ishttps=0;
			 start_char_i=4;
			 start_len1=7;
		 }
		 
		 if(strncasecmp((const char *)url, "https://", 8) == 0){
			 
			 ishttps=1;
			 start_char_i=5;
			 start_len1=8;
		 }		 
		 
		 
		 if(ishttps==0){
		 	 ////改为全局变量式,可以防止内存泄露:
        //server_addr = pvPortMalloc2 strlen(url) - 7);
		 
		 }else{
			 
		 	 ////改为全局变量式,可以防止内存泄露:
        //server_addr = pvPortMalloc2 strlen(url) - 8);
			 
		 }
		 
		 
		 ////改为全局变量式,可以防止内存泄露:
//        if(server_addr == NULL) {
//			  
//			  printf("HTTP_OUT_OF_RAM in malloc server_addr");
//			  
//			  return HTTP_OUT_OF_RAM;
//			  
//			  
//		  }

  printf("proceess 1\r\n");


		 /* 1)提取服务器部分 */
        for(i = start_char_i; url[i]; ++i)
        {
            if (url[i] == ':' && url[i + 1] == '/' && url[i + 2] == '/')
            {
                for (i = i + 3, j = 0; url[i] > 32 && url[i] < 127 && url[i] != '/'; //32-127间的ascII码的字符
                        ++i, ++j)
                {
                    server_addr[j] = url[i];
                    if (url[i] == '@') /* 服务器基础认证符号,我们做不了,遇到就错误. */
                    {
                        return HTTP_AUTH_NOT_SUPPORT;
                    }
                }
                server_addr[j] = '\0';

					 
					 	 ////改为全局变量式,可以防止内存泄露:
                //web_addr = pvPortMalloc2 strlen(url) - start_len1 - strlen((const char *)server_addr));
                //if(web_addr == NULL) return HTTP_OUT_OF_RAM;

                for (k = start_len1 + j; k < (strlen(url)); k++) /* 后半部分提取 */
                {
                    web_addr[k - start_len1 - j] = url[k];
                }

                web_addr[k - start_len1 - j] = '\0';

                while (--j)
                {
                    if (server_addr[j] == ':')//??过滤端口号?
                    {
                        server_addr[j] = '\0';
                    }
                }
            }

        }

        if(strlen((const char *)server_addr) < 2) /* 最短网址3.cn */
        {
          
			  
		     printf("HTTP_SERVER_ADDR_ERROR\r\n");
			  
				
			  
		     printf(server_addr);
			  
			  	 ////改为全局变量式,可以防止内存泄露:
				//vPortFree2 server_addr);
			  
			  	 ////改为全局变量式,可以防止内存泄露:
          //  if(web_addr == NULL) {vPortFree2 web_addr); }
				
				/* 这么短,还不一定提取到了这个. */
			  
				
            return HTTP_SERVER_ADDR_ERROR;
        }
		  
		  printf("\r\nweb host:");

		  printf(server_addr);
		  
		  
		  
        /* 2)查询IP */
         netconn_gethostbyname((const char *)server_addr, &server_ip);

		  
		  
//		  
//		  server_ip.addr=0;
//		  err =  dns_gethostbyname((const char *)server_addr, &server_ip,dns_foundB , NULL);//dns_foundB
//  if (err == ERR_OK)
//  {
//    printf("In cache! IP: %s\n", ipaddr_ntoa(&server_ip));

//  }
//		 
//		  
//		  while(server_ip.addr==0){
//		  
//		  
//		  }
//			  
			   printf("get a IP: %s\n", ipaddr_ntoa(&server_ip));
			  
		  
			if(is_upload_wav==1){
        /* 3)构造访问头 */
				
				
				
        request = pvPortMalloc2( strlen(url) + wav_len1+1024); /* 头所需内存大小. */
				
				
				
				
			}else if(is_upload_wav==0){
				
				  request = pvPortMalloc2( strlen(url) + 1024); /* 头所需内存大小. */
				
			}else if(is_upload_wav==2){
				
				  request = pvPortMalloc2( strlen(url) + 1024); /* 头所需内存大小. */
				
			}
		  
        if(request == NULL) 
			  {
		  
		  
		  printf("HTTP_OUT_OF_RAM in request Malloc.");
		  
		  return HTTP_OUT_OF_RAM;
			  
			  }

			  
			if(is_upload_wav==1){
				
				
				
          #if upload_Wav0_or_pcm1 ==0
         sprintf(request, "POST %s HTTP/1.0\r\nHost: %s\r\nUser-Agent:Mozilla/5.0 (Windows; U; Windows NT 6.1; en-us) AppleWebKit/534.50 (KHTML, like Gecko) Version/5.1 Safari/534.50\r\nContent-Length: %d\r\nContent-Type: audio/wav;rate=8000\r\n\r\n", web_addr, server_addr, wav_len1);
          #endif
				
				
				
          #if upload_Wav0_or_pcm1 ==1
         sprintf(request, "POST %s HTTP/1.0\r\nHost: %s\r\nUser-Agent:Mozilla/5.0 (Windows; U; Windows NT 6.1; en-us) AppleWebKit/534.50 (KHTML, like Gecko) Version/5.1 Safari/534.50\r\nContent-Length: %d\r\nContent-Type: audio/pcm;rate=8000\r\n\r\n", web_addr, server_addr, wav_len1);
          #endif
				
				head_and_wav_len1=strlen(request)+wav_len1;
				
				memcpy( &request[strlen(request)],post,wav_len1);
				
				

			}else if(is_upload_wav==0){				
			  
					  if(post != NULL){
							sprintf(request, "POST %s HTTP/1.0\r\nHost: %s\r\nUser-Agent:Mozilla/5.0 (Windows; U; Windows NT 6.1; en-us) AppleWebKit/534.50 (KHTML, like Gecko) Version/5.1 Safari/534.50\r\nContent-Length: %d\r\nContent-Type: application/x-www-form-urlencoded\r\n\r\n%s", web_addr, server_addr, strlen(post), post);
					  


						 // printf( "POST %s HTTP/1.0\r\nHost: %s\r\nUser-Agent: Mozilla/5.0 (lwip;STM32) TaterLi\r\nContent-Length: %d\r\nContent-Type: application/x-www-form-urlencoded\r\n\r\n%s", web_addr, server_addr, strlen(post), post);
					  
						  
					  }else{
							sprintf(request, "GET %s HTTP/1.0\r\nHost: %s\r\nUser-Agent:Mozilla/5.0 (Windows; U; Windows NT 6.1; en-us) AppleWebKit/534.50 (KHTML, like Gecko) Version/5.1 Safari/534.50\r\n\r\n", web_addr, server_addr);
					  
						  
					  
					  }
		  
	    }else if(is_upload_wav==2){	
			 
			 
			 	sprintf(request, "GET %s HTTP/1.0\r\nHost: %s\r\nUser-Agent:Mozilla/5.0 (Windows; U; Windows NT 6.1; en-us) AppleWebKit/534.50 (KHTML, like Gecko) Version/5.1 Safari/534.50\r\n\r\n", web_addr, server_addr);
					  MP3_return_data_len=0;
			 
		 }
		  
		  //vPortFree2 (server_addr);
        if(web_addr != NULL)
        {
            /* 万一没提取到,就是NULL,如果是NULL,那么也不用继续了. */
			  	 ////改为全局变量式,可以防止内存泄露:
            //vPortFree2 web_addr);
        }
        else
        {
            vPortFree2 (request);
			  
			   printf("HTTP_NOT_VALID_ADDR");
            return HTTP_NOT_VALID_ADDR;
        }
          
		  
        /* 4)开始访问 */
        conn = netconn_new(NETCONN_TCP);
		  	 
		  
        err_msg = netconn_connect(conn, &server_ip, 80); /* 目前也只能支持80端口,比较常用,不考虑特殊情况. */
			
		  

		  
        if (err_msg == ERR_OK)
        {
			    //  struct netbuf *inBuf_g = NULL;
			  
			  
			if(is_upload_wav==1){
            netconn_write(conn, request, head_and_wav_len1, NETCONN_COPY);
				
			}else if(is_upload_wav==0){
			   netconn_write(conn, request, strlen((char *)request), NETCONN_COPY);
				
				
			}else if(is_upload_wav==2){
				
				  netconn_write(conn, request, strlen((char *)request), NETCONN_COPY);
			
				
			}
			
			
            vPortFree2 (request);
            conn->recv_timeout = 15000;//15s
		
            recvPos = 0;

			if(is_upload_wav==2){
				
				u32 offsetptr;
				
		
          void *data;
          u16_t len;
				
	
				

               recvPos = 0;



            ret_lens=0;
				offsetptr=0;
            while(1)
				{
					err=netconn_recv(conn, &inBuf);
					
					if(inBuf==NULL){
						
						break;
					}
               
				do 
            {
              netbuf_data(inBuf, &data, &len);
             
					
					memcpy(MP3_return_data+ret_lens,data,len);
					
						 ret_lens+=len;
					
					
            } 
            while (netbuf_next(inBuf) >= 0);
					

				
					 printf("ret_lens=%d\r\n",ret_lens);
				     netbuf_delete(inBuf);
            }






            // printf (MP3_return_data);






            netconn_close(conn);
            netconn_delete(conn);
           // netbuf_delete(inBuf);
             	
				

				
				
				
				
            /* 5)分析数据(分析HTTP头,暂时不打算支持301之类的)	*/
            for(i = 0; MP3_return_data[i]; ++i)
            {
                if (MP3_return_data[i] == '2' && MP3_return_data[i + 1] == '0' && MP3_return_data[i + 2] == '0')
                {
                    /* 证明200 OK */
                    for(; MP3_return_data[i]!='\0'; ++i)
                    {
                        /* 响应头的结束也是两个回车 */
                        if(MP3_return_data[i] == '\r' && MP3_return_data[i + 1] == '\n' && MP3_return_data[i + 2] == '\r' && MP3_return_data[i + 3] == '\n')
                        {
                            /* 6)复制正文内容 */
                            i += 4;
                            k = ret_lens - i;
                            if(k == 0) return HTTP_NO_CONTENT;

									 
									 MP3_return_data_len=k;
									 
									 MP3_return_data_start_offset=i;
									 
															 
										printf("MP3_return_data_len=%d\r\n",MP3_return_data_len);
										
										
										
										//printf(MP3_return_data);
                            return HTTP_OK;
                        }
                    }
                }
            }
				
				
				
				
				
			}else{
				
				
				
				
          void *data;
          u16_t len;
				
	
				
			   u32 offsetptr;
                recvBuf = pvPortMalloc2( 1024*1024);
					    recvPos = 0;

			
            ret_lens=0;
				offsetptr=0;
            while(1)
				{
							netconn_recv(conn, &inBuf);
							
							if(inBuf==NULL){
								
								break;
							}
							
								
							do 
							{
							  netbuf_data(inBuf, &data, &len);
							 
								
								memcpy(recvBuf+ret_lens,data,len);
								
									 ret_lens+=len;
								
								
							} 
							while (netbuf_next(inBuf) >= 0);
								
							
							recvBuf[ret_lens]='\0';
								
								
							
									netbuf_delete(inBuf);
						
							
							
            }

            netconn_close(conn);
            netconn_delete(conn);
            
             	
				
				
//            if(err_msg != ERR_OK) {
//					
//					 printf("HTTP_OUT_OF_RAM in err_msg != ERR_OK");
//					
//					return HTTP_OUT_OF_RAM;
//					
//					
//					
//				}

				
				
				
            /* 5)分析数据(分析HTTP头,暂时不打算支持301之类的)	*/
            for(i = 0; recvBuf[i]; ++i)
            {
                if (recvBuf[i] == '2' && recvBuf[i + 1] == '0' && recvBuf[i + 2] == '0')
                {
                    /* 证明200 OK */
                    for(; recvBuf[i]!='\0'; ++i)
                    {
                        /* 响应头的结束也是两个回车 */
                        if(recvBuf[i] == '\r' && recvBuf[i + 1] == '\n' && recvBuf[i + 2] == '\r' && recvBuf[i + 3] == '\n')
                        {
                            /* 6)复制正文内容 */
                            i += 4;
                            k = ret_lens - i;
                            if(k == 0) return HTTP_NO_CONTENT;
                            *pageBuf = pvPortMalloc2 (k);
                            if(*pageBuf == NULL)
                            {
                                vPortFree2 (recvBuf);
										 
										 
										 	 printf("HTTP_OUT_OF_RAM in malloc pageBuf");
				
                                return HTTP_OUT_OF_RAM;
                            }
									 
									 memset((char *)*pageBuf,0,k);
									 
                            memcpy((char *)*pageBuf, (const char *)recvBuf + i, k); /* 用HTTP1.0是没http chunked response的.方便处理,否则还要分段接收网页,大的网页反正MCU也接不下. */
                            vPortFree2  (recvBuf);
									 
									 
									 ((char *)*pageBuf)[k]='\0';
									 
									 
									 
                            return HTTP_OK;
                        }
                    }
                }
            }
				
				
			
				printf("NOY_HTTP_OK:");
				
				printf(recvBuf);
				

            if(recvBuf != NULL)	{vPortFree2 (recvBuf);}

				
				
			 }
			
			
				
            return HTTP_NOT_200OK;
        }
        else
        {
            vPortFree2 (request);
			   printf("HTTP_SERVER_REFUSE");
            return HTTP_SERVER_REFUSE;
        }

    }
    else
    {
		 
		 printf("HTTPS_NOT_SUPPORT");
		 
        return HTTPS_NOT_SUPPORT;
    }
}

 

上面这个实现了单片机调用网站地址并返回网页内容,下面就用这个函数具体调用百度http://vop.baidu.com/server_api?dev_pid=1536&cuid=%s&token=%s 接口,

哈,只能展示这么多,更详细支持请联系我 qq790861133  ,或进入 我网店 https://shop454934838.taobao.com 购买我的百度语音识别模块


void process_asr(){
	
	int err = HTTP_OK;
	  uint16_t  ret_code1; 
	
		  
					// printf("start ASR...");
						 
		  					  
				//------------------------------------------------------------------------------------
  
				 reflsh_token(0);
		       
					 
					memset(urlgg,'\0',urlchar_maxlen);
					  
					  //dev_pid=1536是普通话,1537	=普通话(纯中文识别),dev_pid=1936是远场普通话
					 sprintf(urlgg,"http://vop.baidu.com/server_api?dev_pid=1536&cuid=%s&token=%s",cuid,g_access_token);
					
	
		  
		  
						 err = WebClient(urlgg, reco_temp_ram, &abuf,1,reco_temp_ram_len);
						 
						 
		  
						 
						 if(abuf != NULL && err == HTTP_OK)
						  {
。。。。。。。。。。。。。。。。。

 

你可能感兴趣的:(原创)