[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: [lwip-users] Assert "tcp_slowtmr" in tcp.c reached
From: |
Marco Jakobs |
Subject: |
Re: [lwip-users] Assert "tcp_slowtmr" in tcp.c reached |
Date: |
Tue, 02 Feb 2010 16:29:53 +0100 |
User-agent: |
Thunderbird 2.0.0.23 (Windows/20090812) |
Kieran Mansley schrieb:
Could you send it to the list so that others who are interested can see
the code too?
Sure ... i was not sure if attachments are welcome here.
The RTOS task "AppIP" is responsible for initialization of the LwIP and
PPP handling. There is also a bunch of test code in it. The important
areas are:
LwIP Init: Line 138
PPP start connection: Line 244
PPP close connection: Line 277
Marco
/***************************************************************************
* AppIP - Takes care of PPP and ethernet connections.
* Copyright (c) 2009 © Funk-Electronics Picorgros GmbH
*
* TODO:
* - The main task is passed a pointer to the network interfaces. We
* have a race condition if the PPP link would went down in a few
* microseconds before the main task has been scheduled. In this
* case the main task would have an pointer to a no longer existing
* network interface.
*
* $Id: AppIP.c 731 2009-12-18 20:42:41Z jakobs $
***************************************************************************/
/* ----------------------- System includes --------------------------------*/
#include "FreeRTOS.h"
#include "task.h"
#include <stdarg.h>
#include <stdio.h>
#include "lwip/init.h"
#include "lwip/api.h"
#include "lwip/tcpip.h"
#include "lwip/ip.h"
#include "ppp.h"
#include "nat.h"
/* ----------------------- Project includes -------------------------------*/
#include "AppIP.h"
#include "Libraries\lwIP\port\EMAC\SAM7_EMAC.h"
#include "confreg_ext.h"
#include "tmo_ext.h"
/* ----------------------- Defines ----------------------------------------*/
#define APPIP_DEBUG ( 0 )
#if APPIP_DEBUG == 1
#define APPIP_TRACE(x) do { vSysDiag x; } while(0)
#else
#define APPIP_TRACE(x)
#endif
//#define PPP_USER "test"
//#define PPP_PASS "test"
#define MODEM_GPRS ( 0 )
#define MODEM_TETRA ( 1 )
#define MODEM_NULL ( 2 )
#define MODEM ( MODEM_NULL )
#if MODEM == MODEM_GPRS
#define PPP_DUMMY_STRING "at\r\n"
#define PPP_HANGUP_STRING "ath0\r\n"
#define PPP_INIT_STRING_0 "ate0\r\n"
#define PPP_INIT_STRING_1 "at+cpin=4711\r\n"
#define PPP_INIT_STRING_2
"at+cgdcont=1,\"IP\",\"internet.eplus.de\"\r\n"
#define PPP_DIAL_STRING "atdt*99***1#\r\n"
#elif MODEM == MODEM_TETRA
#define PPP_DUMMY_STRING "at\r\n"
#define PPP_HANGUP_STRING "ath0\r\n"
#define PPP_INIT_STRING_0 "ate0\r\n"
#define PPP_DIAL_STRING "atd*99#\r\n"
#elif MODEM == MODEM_NULL
#else
#error "no modem set!"
#endif
#define PPP_DIAL_CONNECT_WAITMAX 10000
#define PPP_DIAL_CONNECT_OKAY "\r\nCONNECT\r\n"
/* ----------------------- Type Definitions -------------------------------*/
typedef enum
{
STATE_INIT,
STATE_IDLE,
STATE_MODEM_INIT,
STATE_MODEM_DIAL,
STATE_MODEM_WAIT_CONNECT,
STATE_PPP_INIT,
STATE_PPP_ISOPEN,
STATE_PPP_CLOSE_WAIT_SHUTDOWN,
STATE_PPP_CLOSE
} eAppIPState_t;
typedef enum
{
PPP_MSG_PPP_LINKREADY,
PPP_MSG_PPP_LINKDEAD,
PPP_MSG_PPP_CLOSE_FINALIZED
} ePPPMsg_t;
/* ----------------------- Global variables -------------------------------*/
extern volatile unsigned char eth_link_status; //
Merker für Linkstatus aus SAM7_emac.c
/* ----------------------- Static variables -------------------------------*/
static xAppIP_CFG_t xCurCFG;
static eAppIPState_t eState;
static int ppp_con_fd;
static struct netif xEMAC_if;
static struct netif *pxPPP_if;
/* ----------------------- Static functions -------------------------------*/
static void vAppDumpInMessage( const xAppIP_MsgIn_t * pxInMsg );
static void vModemSend( sio_fd_t xFd, const char *pszCommand );
static void vModemRead( sio_fd_t xFd, char *pszBuffer, int iBufferMax );
static void vPPPStatusCB( void *ctx, int errCode, void *arg );
static const char *vPPPStatusStrError( int errCode );
void ppp_trace( int level, const char *format, ... );
/* ----------------------- Prototypes -------------------------------------*/
extern err_t ethernetif_init( struct netif *netif );
/* ----------------------- Start implementation ---------------------------*/
void
vAppIP( void *pvIPCFG )
{
xAppIP_MsgIn_t xMsgIn;
portBASE_TYPE pdResult;
char arucRcvBuffer[32];
u32_t uiBufferCurPos;
portTickType xTickWaitStart, xTickDelta;
ePPPMsg_t eMsg;
int err;
xAppIP_MsgOut_t xMsgOut;
char f,ppp_user[21],ppp_pass[21];
// Username und Password kopieren
ppp_user[20]=0;
ppp_pass[20]=0;
for (f=0;f<10;f++)
{
ppp_user[f*2]=kreg[350+f]>>8;
ppp_user[f*2+1]=kreg[350+f]&0xff;
ppp_pass[f*2]=kreg[360+f]>>8;
ppp_pass[f*2+1]=kreg[360+f]&0xff;
}
/* Initialize IP stack */
tcpip_init( NULL, NULL );
pppInit( );
pppSetAuth( PPPAUTHTYPE_PAP, &ppp_user[0], &ppp_pass[0] );
PORT_ASSERT( NULL != pvIPCFG );
memcpy( &xCurCFG, pvIPCFG, sizeof( xAppIP_CFG_t ) );
eState = STATE_INIT;
for( ;; )
{
switch ( eState )
{
case STATE_INIT:
netif_add( &xEMAC_if, &( xCurCFG.xETHCfg.xETHIP ), &(
xCurCFG.xETHCfg.xETHNetmask ),
&( xCurCFG.xETHCfg.xETHGateway ), NULL, ethernetif_init,
tcpip_input );
netif_set_default( &xEMAC_if );
netif_set_up( &xEMAC_if );
xMsgOut.eMsgType = MSGOUT_ETHERNET_ISOPEN;
xMsgOut.x.xMSGEthernetOpen.nif = &xEMAC_if;
pdResult = xQueueSend( xCurCFG.xMsgQueueOut, &xMsgOut, sizeof(
xMsgOut ) );
PORT_ASSERT( pdTRUE == pdResult );
eState = STATE_IDLE;
break;
case STATE_IDLE:
pdResult = xQueueReceive(
xCurCFG.xMsgQueueIn, &xMsgIn, portMAX_DELAY );
if( pdTRUE == pdResult )
{
//vSysDiag("MsgQueueIn receive State Idle\r\n");
vAppDumpInMessage( &xMsgIn );
switch ( xMsgIn.eMsgType )
{
case MSGIN_DO_OPEN_PPPLINK:
APPIP_TRACE( ( "vAppIP(STATE_IDLE): opening new PPP
link...\r\n" ) );
eState = STATE_MODEM_INIT;
break;
default:
APPIP_TRACE( ( "vAppIP(STATE_IDLE): received unknown
message. ignoring it.\r\n" ) );
break;
}
}
break;
case STATE_MODEM_INIT:
eState = STATE_MODEM_DIAL;
break;
case STATE_MODEM_DIAL:
#if MODEM == MODEM_NULL
#elif MODEM == MODEM_GPRS
vModemSend( xCurCFG.xMODEMCfg.xMODEMfd, PPP_DUMMY_STRING );
vTaskDelay( 1000 );
vModemRead( xCurCFG.xMODEMCfg.xMODEMfd, arucRcvBuffer, sizeof(
arucRcvBuffer ) );
APPIP_TRACE( ( "vAppIP(STATE_MODEM_DIAL): sent='%s',
received='%s'\r\n", PPP_DUMMY_STRING, arucRcvBuffer ) );
vModemSend( xCurCFG.xMODEMCfg.xMODEMfd, PPP_HANGUP_STRING );
vTaskDelay( 1000 );
vModemRead( xCurCFG.xMODEMCfg.xMODEMfd, arucRcvBuffer, sizeof(
arucRcvBuffer ) );
APPIP_TRACE( ( "vAppIP(STATE_MODEM_DIAL): sent='%s',
received='%s'\r\n", PPP_HANGUP_STRING, arucRcvBuffer ) );
vModemSend( xCurCFG.xMODEMCfg.xMODEMfd, PPP_INIT_STRING_0 );
vTaskDelay( 1000 );
vModemRead( xCurCFG.xMODEMCfg.xMODEMfd, arucRcvBuffer, sizeof(
arucRcvBuffer ) );
APPIP_TRACE( ( "vAppIP(STATE_MODEM_DIAL): sent='%s',
received='%s'\r\n", PPP_INIT_STRING_0, arucRcvBuffer ) );
vModemSend( xCurCFG.xMODEMCfg.xMODEMfd, PPP_INIT_STRING_1 );
vTaskDelay( 5000 );
vModemRead( xCurCFG.xMODEMCfg.xMODEMfd, arucRcvBuffer, sizeof(
arucRcvBuffer ) );
APPIP_TRACE( ( "vAppIP(STATE_MODEM_DIAL): sent='%s',
received='%s'\r\n", PPP_INIT_STRING_1, arucRcvBuffer ) );
vModemSend( xCurCFG.xMODEMCfg.xMODEMfd, PPP_INIT_STRING_2 );
vTaskDelay( 1000 );
vModemRead( xCurCFG.xMODEMCfg.xMODEMfd, arucRcvBuffer, sizeof(
arucRcvBuffer ) );
APPIP_TRACE( ( "vAppIP(STATE_MODEM_DIAL): sent='%s',
received='%s'\r\n", PPP_INIT_STRING_2, arucRcvBuffer ) );
vModemSend( xCurCFG.xMODEMCfg.xMODEMfd, PPP_DIAL_STRING );
vTaskDelay( 1000 );
vModemRead( xCurCFG.xMODEMCfg.xMODEMfd, arucRcvBuffer, sizeof(
arucRcvBuffer ) );
APPIP_TRACE( ( "vAppIP(STATE_MODEM_DIAL): sent='%s',
received='%s'\r\n", PPP_DIAL_STRING, arucRcvBuffer ) );
#elif MODEM == MODEM_TETRA
vModemSend( xCurCFG.xMODEMCfg.xMODEMfd, PPP_DUMMY_STRING );
vTaskDelay( 1000 );
vModemRead( xCurCFG.xMODEMCfg.xMODEMfd, arucRcvBuffer, sizeof(
arucRcvBuffer ) );
APPIP_TRACE( ( "vAppIP(STATE_MODEM_DIAL): sent='%s',
received='%s'\r\n", PPP_DUMMY_STRING, arucRcvBuffer ) );
vModemSend( xCurCFG.xMODEMCfg.xMODEMfd, PPP_HANGUP_STRING );
vTaskDelay( 1000 );
vModemRead( xCurCFG.xMODEMCfg.xMODEMfd, arucRcvBuffer, sizeof(
arucRcvBuffer ) );
APPIP_TRACE( ( "vAppIP(STATE_MODEM_DIAL): sent='%s',
received='%s'\r\n", PPP_HANGUP_STRING, arucRcvBuffer ) );
vModemSend( xCurCFG.xMODEMCfg.xMODEMfd, PPP_INIT_STRING_0 );
vTaskDelay( 1000 );
vModemRead( xCurCFG.xMODEMCfg.xMODEMfd, arucRcvBuffer, sizeof(
arucRcvBuffer ) );
APPIP_TRACE( ( "vAppIP(STATE_MODEM_DIAL): sent='%s',
received='%s'\r\n", PPP_INIT_STRING_0, arucRcvBuffer ) );
vModemSend( xCurCFG.xMODEMCfg.xMODEMfd, PPP_DIAL_STRING );
vTaskDelay( 1000 );
vModemRead( xCurCFG.xMODEMCfg.xMODEMfd, arucRcvBuffer, sizeof(
arucRcvBuffer ) );
APPIP_TRACE( ( "vAppIP(STATE_MODEM_DIAL): sent='%s',
received='%s'\r\n", PPP_DIAL_STRING, arucRcvBuffer ) );
#endif
eState = STATE_PPP_INIT;
break;
case STATE_PPP_INIT:
ppp_con_fd = -1;
ppp_con_fd = pppOverSerialOpen( xCurCFG.xMODEMCfg.xMODEMfd,
vPPPStatusCB, NULL );
APPIP_TRACE( ( "vAppIP(STATE_PPP_INIT): opening ppp connection\r\n"
) );
eState = STATE_PPP_ISOPEN;
break;
case STATE_PPP_ISOPEN:
pdResult = xQueueReceive( xCurCFG.xMsgQueueIn, &xMsgIn, 1000 );
if( pdTRUE == pdResult )
{
//vSysDiag("MsgQueueIn receive State PPP_ISOPEN\r\n");
switch (
xMsgIn.eMsgType )
{
case MSGIN_INTERNAL:
eMsg = xMsgIn.x.xMSGInternal.iMsg;
switch ( eMsg )
{
case PPP_MSG_PPP_LINKREADY:
xMsgOut.eMsgType = MSGOUT_PPPLINK_ISOPEN;
xMsgOut.x.xMSGEthernetOpen.nif = pxPPP_if;
pdResult = xQueueSend( xCurCFG.xMsgQueueOut, &xMsgOut,
sizeof( xMsgOut ) );
PORT_ASSERT( pdTRUE == pdResult );
break;
case PPP_MSG_PPP_LINKDEAD:
eState = STATE_PPP_CLOSE;
break;
default:
APPIP_TRACE( ( "vAppIP(STATE_PPP_ISOPEN): received
unknown internal message %d. ignoring it.\r\n",
( int )eMsg ) );
break;
}
break;
case MSGIN_DO_SHUTDOWN_PPPLINK:
err = pppClose( ppp_con_fd );
PORT_ASSERT( 0 == err );
eState = STATE_PPP_CLOSE_WAIT_SHUTDOWN;
break;
default:
APPIP_TRACE( ( "vAppIP(STATE_PPP_ISOPEN): received unknown
message %d. ignoring it.\r\n",
( int )xMsgIn.eMsgType ) );
break;
}
}
else
{
APPIP_TRACE( ( "vAppIP(STATE_PPP_ISOPEN): no events
pending\r\n" ) );
}
break;
case STATE_PPP_CLOSE_WAIT_SHUTDOWN:
APPIP_TRACE( ( "vAppIP(STATE_PPP_CLOSE_WAIT_SHUTDOWN): PPP link
waiting for shutdown...\r\n" ) );
pdResult = xQueueReceive( xCurCFG.xMsgQueueIn, &xMsgIn, 1000 );
if( pdTRUE == pdResult )
{
//vSysDiag("MsgQueueIn receive State PPP_CLOSE_WAIT_SHUTDOWN\r\n");
switch ( xMsgIn.eMsgType )
{
case MSGIN_INTERNAL:
eMsg = xMsgIn.x.xMSGInternal.iMsg;
switch ( eMsg )
{
case PPP_MSG_PPP_LINKDEAD:
eState = STATE_PPP_CLOSE;
break;
default:
APPIP_TRACE( ( "vAppIP(STATE_PPP_CLOSE_WAIT_SHUTDOWN):
received unknown internal message %d. ignoring it.\r\n", ( int )eMsg ) );
break;
}
break;
default:
APPIP_TRACE( ( "vAppIP(STATE_PPP_CLOSE_WAIT_SHUTDOWN):
received unknown message %d. ignoring it.\r\n",
( int )xMsgIn.eMsgType ) );
break;
}
}
break;
case STATE_PPP_CLOSE:
xMsgOut.eMsgType = MSGOUT_PPPLINK_ISDEAD;
xMsgOut.x.xMSGEthernetOpen.nif = pxPPP_if;
pdResult = xQueueSend( xCurCFG.xMsgQueueOut, &xMsgOut, sizeof(
xMsgOut ) );
PORT_ASSERT( pdTRUE == pdResult );
APPIP_TRACE( ( "vAppIP(STATE_PPP_CLOSE): Switching to state idle
after close...\r\n" ) );
eState = STATE_IDLE;
break;
default:
PORT_ASSERT( 0 );
break;
}
}
}
// Reports Link status (1=Link online, 0=Link offline)
unsigned char get_eth_link(void)
{
if (eth_link_status==1) return (1); else return (0);
}
static void
vAppDumpInMessage( const xAppIP_MsgIn_t * pxInMsg )
{
APPIP_TRACE( ( "msg type: %d\r\n", ( int )pxInMsg->eMsgType ) );
}
static void
vModemSend( sio_fd_t xFd, const char *pszCommand )
{
sio_write( xFd, ( char * )pszCommand, strlen( pszCommand ) );
}
static void
vModemRead( sio_fd_t xFd, char *pszBuffer, int iBufferMax )
{
int iBytesLeft = iBufferMax - 1; /* One space for
terminating character. */
char *pszBufferCur = pszBuffer;
u32_t uiBytesReadCur;
portTickType xTickWaitStart, xTickDelta, xAllowedTickDelta = 5000;
xTickWaitStart = xTaskGetTickCount( );
do
{
uiBytesReadCur = sio_read( xFd, pszBufferCur, iBytesLeft );
if( uiBytesReadCur > 0 )
{
xAllowedTickDelta = 10;
pszBufferCur += uiBytesReadCur;
iBytesLeft -= uiBytesReadCur;
xTickWaitStart = xTaskGetTickCount( );
}
else
{
/* Always take care when tick counter might overflow. */
xTickDelta = xTaskGetTickCount( ) - xTickWaitStart;
}
}
while( ( xTickDelta < xAllowedTickDelta ) && ( iBytesLeft > 0 ) );
*pszBufferCur = '\0';
}
static const char *
vPPPStatusStrError( int errCode )
{
const char *retval;
switch ( errCode )
{
case PPPERR_NONE:
retval = "none";
break;
case PPPERR_PARAM:
retval = "param";
break;
case PPPERR_OPEN:
retval = "open";
break;
case PPPERR_DEVICE:
retval = "device";
break;
case PPPERR_ALLOC:
retval = "alloc";
break;
case PPPERR_USER:
retval = "user";
break;
case PPPERR_CONNECT:
retval = "connect";
break;
case PPPERR_AUTHFAIL:
retval = "authfail";
break;
case PPPERR_PROTOCOL:
retval = "protocol";
break;
case PPPERR_IFUP:
retval = "ifup";
break;
default:
retval = "unknown";
break;
}
return retval;
}
static void
vPPPStatusCB( void *ctx, int errCode, void *arg )
{
xAppIP_MsgIn_t eMsg;
portBASE_TYPE pdStatus;
ip_nat_entry_t new_nat_entry;
( void )ctx;
APPIP_TRACE( ( "vPPPStatusCB: error code = %s\r\n", vPPPStatusStrError(
errCode ) ) );
switch ( errCode )
{
case PPPERR_NONE:
APPIP_TRACE( ( "vPPPStatusCB: PPP link reported connection
established.\r\n" ) );
break;
case PPPERR_IFUP:
APPIP_TRACE( ( "vPPPStatusCB: PPP link reported network interface is
up.\r\n" ) );
pxPPP_if = ( struct netif * )arg;
new_nat_entry.out_if = ( struct netif * )pxPPP_if;
new_nat_entry.in_if = ( struct netif * )&xEMAC_if;
// IP4_ADDR( &new_nat_entry.source_net, 92, 168, 0, 100 );
// NAT nur von diesem Rechner ...
// IP4_ADDR( &new_nat_entry.source_netmask, 255, 255, 255, 255 );
// IP4_ADDR( &new_nat_entry.dest_net, 192, 168, 0, 0 );
// ... in dieses Netzwerk
// IP4_ADDR( &new_nat_entry.dest_netmask, 255, 255, 255, 0 );
IP4_ADDR( &new_nat_entry.source_net, kreg[460]>>8, kreg[460],
kreg[461]>>8, kreg[461] ); // hier wird alles genattet
IP4_ADDR( &new_nat_entry.source_netmask, kreg[462]>>8, kreg[462],
kreg[463]>>8, kreg[463] );
IP4_ADDR( &new_nat_entry.dest_net, kreg[464]>>8, kreg[464],
kreg[465]>>8, kreg[465] );
IP4_ADDR( &new_nat_entry.dest_netmask, kreg[466]>>8, kreg[466],
kreg[467]>>8, kreg[467] );
vSysDiag("NAT initialized
%hu.%hu.%hu.%hu/%hu.%hu.%hu.%hu to %hu.%hu.%hu.%hu/%hu.%hu.%hu.%hu\r\n",\
kreg[460]>>8,kreg[460]&0xff,kreg[461]>>8,kreg[461]&0xff,\
kreg[462]>>8,kreg[462]&0xff,kreg[463]>>8,kreg[463]&0xff,\
kreg[464]>>8,kreg[464]&0xff,kreg[465]>>8,kreg[465]&0xff,\
kreg[466]>>8,kreg[466]&0xff,kreg[467]>>8,kreg[467]&0xff);
ip_nat_init( &new_nat_entry );
eMsg.eMsgType = MSGIN_INTERNAL;
eMsg.x.xMSGInternal.iMsg = PPP_MSG_PPP_LINKREADY;
//vSysDiag("MsgQueueIn send PPPERR_IFUP\r\n");
pdStatus = xQueueSend( xCurCFG.xMsgQueueIn,
&eMsg, sizeof( eMsg ) );
PORT_ASSERT( pdTRUE == pdStatus );
break;
case PPPERR_PROTOCOL:
case PPPERR_CONNECT:
case PPPERR_USER:
break;
case PPPERR_SHUTDOWN:
ip_nat_remove_all( );
pxPPP_if = NULL;
eMsg.eMsgType = MSGIN_INTERNAL;
eMsg.x.xMSGInternal.iMsg = PPP_MSG_PPP_LINKDEAD;
APPIP_TRACE( ( "vPPPStatusCB: PPP link is now dead.\r\n" ) );
//vSysDiag("MsgQueueIn send
PPPERR_SHUTDOWN\r\n");
pdStatus = xQueueSend( xCurCFG.xMsgQueueIn,
&eMsg, sizeof( eMsg ) );
PORT_ASSERT( pdTRUE == pdStatus );
break;
default:
APPIP_TRACE( ( "vPPPStatusCB: unhandled error code!\r\n" ) );
PORT_ASSERT( 0 );
break;
}
}
void
ppp_trace( int level, const char *format, ... )
{
va_list ap;
static char szDebugBuffer[160];
( void )level;
va_start( ap, format );
vsnprintf( szDebugBuffer, sizeof( szDebugBuffer ), format, ap );
vSysDiag( "%s", szDebugBuffer );
va_end( ap );
}
- Re: [lwip-users] How to calculate the memory size used by lwIP?, (continued)
- [lwip-users] Assert "tcp_slowtmr" in tcp.c reached, Marco Jakobs, 2010/02/02
- Re: [lwip-users] Assert "tcp_slowtmr" in tcp.c reached, Kieran Mansley, 2010/02/02
- Re: [lwip-users] Assert "tcp_slowtmr" in tcp.c reached, Marco Jakobs, 2010/02/02
- Re: [lwip-users] Assert "tcp_slowtmr" in tcp.c reached, Kieran Mansley, 2010/02/02
- Re: [lwip-users] Assert "tcp_slowtmr" in tcp.c reached, Simon Goldschmidt, 2010/02/02
- Re: [lwip-users] Assert "tcp_slowtmr" in tcp.c reached, Marco Jakobs, 2010/02/02
- Re: [lwip-users] Assert "tcp_slowtmr" in tcp.c reached, Simon Goldschmidt, 2010/02/02
- Re: [lwip-users] Assert "tcp_slowtmr" in tcp.c reached, Marco Jakobs, 2010/02/02
- Re: [lwip-users] Assert "tcp_slowtmr" in tcp.c reached, Kieran Mansley, 2010/02/02
- Re: [lwip-users] Assert "tcp_slowtmr" in tcp.c reached,
Marco Jakobs <=
Re: [lwip-users] Assert "tcp_slowtmr" in tcp.c reached, Simon Goldschmidt, 2010/02/02