STM32407+LWIP+EC20 PPP拨号流程

先初始化EC20 主要有以下AT指令 可以根据需要增加 注意LWIP+EC20 PPP 只能使用软件检验 

所以不能打开 CHECKSUM_BY_HARDWARE 这个宏定义

"+++"            //退出透传模式

"ATE0\r\n"            //关掉回显

"AT+CPIN?\r\n"        //查询SIM卡的状态

"AT+CSQ\r\n"             //Signal Quality Report 检查网络信号强度和SIM卡情况

"AT+CREG?\r\n"         //查询网络注册信息

"AT+CGREG?\r\n"         //查询无线分组业务

"AT+QIACT?\r\n"        //获取本地IP地址 contextID=1

"AT+QIACT=1\r\n"        //Activate a PDP Context 激活移动场景contextID=1

"AT+CGSN\r\n"        //Query IMEI

"AT+QCCID\r\n"        //Query CCID

LWIP PPP初始化流程如下

u8 lwip_PPP_comm_init(void)
{
    uint8_t ctx = 0;
    while(EC20_status_check()) 
    {
        sys_msleep(1000);
         ctx = 0;
    }
    EC20_PPP(); //"ATD*99#\r\n"
    ppp_modle=1;
    
    tcpip_init(NULL,NULL);
    netif_set_status_callback(&lwip_netif, netif_status_callback);
    netif_set_link_callback(&lwip_netif, netif_link_callback);
    netif_set_remove_callback(&lwip_netif, netif_remove_callback);
    ppp = pppos_create( &lwip_netif, output_cb, status_cb, &ctx );
    sys_thread_new("PppRead", PppRead, NULL, 1024, LWIP_GETDATA_TASK_PRIO);
    
    if( ppp_connect(ppp, 0) != ERR_OK )
    {
        while(1)
        {
            sys_msleep(1000);
        }
    }

    ppp_set_default(ppp);
    return ctx;
}

EC20_status_check 是EC20初始化和状态检测

EC20_PPP(); //"ATD*99#\r\n"

uint32_t output_cb(ppp_pcb *pcb, uint8_t *data, uint32_t len, void *ctx) 写数据

uint32_t output_cb(ppp_pcb *pcb, uint8_t *data, uint32_t len, void *ctx) {
    if(ppp_modle)
    {
       //往串口发送数据
    }
        return 0;
}

void status_cb(ppp_pcb *pcb, int err_code, void *ctx) 状态改变回调函数 使用LWIP文档提供的示例

void status_cb(ppp_pcb *pcb, int err_code, void *ctx) {
  struct netif *pppif = ppp_netif(pcb);
  LWIP_UNUSED_ARG(ctx);

  switch(err_code) {
    case PPPERR_NONE: {
#if LWIP_DNS
      const ip_addr_t *ns;
#endif /* LWIP_DNS */
      PPP_PRINT("status_cb: Connected\n");
#if PPP_IPV4_SUPPORT
      PPP_PRINT("   our_ipaddr  = %s\n", ipaddr_ntoa(&pppif->ip_addr));
      PPP_PRINT("   his_ipaddr  = %s\n", ipaddr_ntoa(&pppif->gw));
      PPP_PRINT("   netmask     = %s\n", ipaddr_ntoa(&pppif->netmask));
      ppp_conn_success = 1;
#if LWIP_DNS
      ns = (ip_addr_t*)dns_getserver(0);
      PPP_PRINT("   dns1        = %s\n", ipaddr_ntoa(ns));
      ns = (ip_addr_t*)dns_getserver(1);
      PPP_PRINT("   dns2        = %s\n", ipaddr_ntoa(ns));
            ns = ns;
            pppif = pppif;
#endif /* LWIP_DNS */
#endif /* PPP_IPV4_SUPPORT */
#if PPP_IPV6_SUPPORT
      PPP_PRINT("   our6_ipaddr = %s\n", ip6addr_ntoa(netif_ip6_addr(pppif, 0)));
#endif /* PPP_IPV6_SUPPORT */
      break;
    }
    case PPPERR_PARAM: {
      PPP_PRINT("status_cb: Invalid parameter\n");
      break;
    }
    case PPPERR_OPEN: {
      PPP_PRINT("status_cb: Unable to open PPP session\n");
      break;
    }
    case PPPERR_DEVICE: {
      PPP_PRINT("status_cb: Invalid I/O device for PPP\n");
      break;
    }
    case PPPERR_ALLOC: {
      PPP_PRINT("status_cb: Unable to allocate resources\n");
      break;
    }
    case PPPERR_USER: {
      PPP_PRINT("status_cb: User interrupt\n");
      break;
    }
    case PPPERR_CONNECT: {
      PPP_PRINT("status_cb: Connection lost\n");
      break;
    }
    case PPPERR_AUTHFAIL: {
      PPP_PRINT("status_cb: Failed authentication challenge\n");
      break;
    }
    case PPPERR_PROTOCOL: {
      PPP_PRINT("status_cb: Failed to meet protocol\n");
      break;
    }
    case PPPERR_PEERDEAD: {
      PPP_PRINT("status_cb: Connection timeout\n");
      break;
    }
    case PPPERR_IDLETIMEOUT: {
      PPP_PRINT("status_cb: Idle Timeout\n");
      break;
    }
    case PPPERR_CONNECTTIME: {
      PPP_PRINT("status_cb: Max connect time reached\n");
      break;
    }
    case PPPERR_LOOPBACK: {
      PPP_PRINT("status_cb: Loopback detected\n");
      break;
    }
    default: {
      PPP_PRINT("status_cb: Unknown error code %d\n", err_code);
      break;
    }
  }

/*
 * This should be in the switch case, this is put outside of the switch
 * case for example readability.
 */

  if (err_code == PPPERR_NONE) {
    return;
  }

  /* ppp_close() was previously called, don't reconnect */
  if (err_code == PPPERR_USER) {
    /* ppp_free(); -- can be called here */
    return;
  } 
  ppp_conn_success = 0;
  /*
   * Try to reconnect in 30 seconds, if you need a modem chatscript you have
   * to do a much better signaling here ;-)
   */
  ppp_connect(pcb, 30);
  /* OR ppp_listen(pcb); */
}

void PppRead( void  * argument ) 读取串口数据给LWIP内核

void PppRead( void  * argument )
{
    uint8_t Readbuf[512];
    uint32_t recv_size,timeout=0; 
    while(1)
    {
        if( ppp )
        {
            recv_size =0;
            if(ppp_modle)
            {
                recv_size = uart_ReadData(Readbuf,sizeof(Readbuf));
                if( recv_size)
                {
                    pppos_input_tcpip(ppp, Readbuf, recv_size );//0x7e
                }

             }
                
            sys_msleep(5);
        }
        else
        {
            sys_msleep(100);
        }
    }
}

STM32是一款广泛应用于嵌入式系统的微控制器,而EC200S是一款支持GSM/GPRS/EDGE/UMTS/HSPA+/LTE等多种网络技术的无线模块。要在STM32上通过EC200S拨号上网,可以按照以下步骤进行: 1. 硬件接线:将EC200S无线模块与STM32微控制器进行连接。具体连接方式可以参考EC200SSTM32的开发板手册或者电路图。 2. 配置串口通信:在STM32的软件开发环境中,配置一个串口通信通道,用于与EC200S进行数据通信。通常情况下,EC200S使用AT指令进行控制和通信,因此选择一个串口作为EC200S的通信端口,并配置相应的参数,例如波特率、数据位数、校验位等。 3. 编写软件代码:在STM32的开发环境中,编写相应的软件代码。首先,通过串口向EC200S发送AT指令,例如AT+CGDCONT指令用于设置移动网络接入点;然后使用ATD*99#指令拨号上网;最后,通过串口接收和解析EC200S返回的数据,以确定拨号是否成功。 4. 处理网络连接状态:在程序中处理网络连接状态。一旦成功拨号上网STM32可以通过发送和接收数据来与互联网进行通信。如果网络连接中断或者拨号失败,STM32可以尝试重新拨号或者处理错误情况。 需要注意的是,具体的实现可能还需要针对EC200S模块的功能特性和STM32的硬件限制进行适当调整和优化。此外,还需要参考相关的技术文档和开发资料,以确保正确配置和操作各个模块和接口。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值