コード例 #1
0
// called from a system async event handler whenever g_easyConfigCtx.isWifiNeedToConfigure is true
void WiFi_EasyConfigTask(void)
{
    switch (g_easyConfigCtx.state)
    {
        case EZ_WAIT_FOR_START:
            SYS_CONSOLE_MESSAGE("EZ_WAIT_FOR_START\r\n");
            g_easyConfigCtx.isWifiNeedToConfigure = false;
            // first thing to do is delay one second so user can see on the web
            // page that disconnect is about occur in process of connecting to
            // designated AP.  So create and start timer.
            g_easyConfigCtx.timer = SYS_TICK_TimerCreate(EasyConfigTimerHandler);
            SYS_TICK_TimerSetRate(g_easyConfigCtx.timer, SYS_TICK_TicksPerSecondGet() * WF_EASY_CONFIG_DELAY_TIME);
            g_easyConfigCtx.state = EZ_WAIT_FOR_DELAY;
            break;

        case EZ_WAIT_FOR_DELAY:
            SYS_CONSOLE_MESSAGE("EZ_WAIT_FOR_DELAY\r\n");
            g_easyConfigCtx.isWifiNeedToConfigure = false;
            
            // delete timer now that delay has occurred
            SYS_TICK_TimerDelete(g_easyConfigCtx.timer);

            // connect to AP that user selected on web page
            EasyConfigConnect();
            g_easyConfigCtx.state = EZ_WAIT_FOR_START;

            break;
        }
}
コード例 #2
0
ファイル: dyn_dns.c プロジェクト: webgou/Equinox-Clock
/****************************************************************************
  Function:
    void DDNSInit(void)

  Summary:
    Initializes the Dynamic DNS module.

  Description:
  	This function initializes the Dynamic DNS client.  It clears the 
  	DDNSClient pointers structure, and tells the module to attempt the 
  	first update after 15 seconds have elapsed (so as to allow the DHCP
  	configuration to stabalize).

  Precondition:
	None

  Parameters:
	None

  Returns:
	None
    
  Remarks:
	This function is called only one during lifetime of the application.
  ***************************************************************************/
bool DDNSInit(const TCPIP_STACK_MODULE_CTRL* const stackData,
              const DDNS_MODULE_GONFIG* const ddnsData)
{
	if (stackData->stackAction == TCPIP_STACK_ACTION_IF_UP)
    {   // interface restart
        return true;
    }
	
	if (!IfUp)
	{
		// Clear the Dynamic DNS Client to start
		memset((void*)&DDNSClient, 0x00, sizeof(DDNSClient));
		
		// Use the default Check IP server
		DDNSClient.ROMPointers.CheckIPServer = 1;
		DDNSClient.CheckIPServer.szROM = DDNS_CHECKIP_SERVER;
		DDNSClient.CheckIPPort = DDNS_DEFAULT_PORT;

		// First update is 15 seconds after boot, allowing DHCP to stabilize
		dwUpdateAt = SYS_TICK_Get() + 15*SYS_TICK_TicksPerSecondGet();
		bForceUpdate = true;
		lastStatus = DDNS_STATUS_UNKNOWN;
	}
	
	IfUp++;
	
	return true;
}
コード例 #3
0
/*********************************************************************
  Function:
  	static SYS_TICK SNMPGetTimeStamp(void)
                                   
  Summary:
	Obtains the current Tick value for the SNMP time stamp.

  Description:
	This function retrieves the absolute time measurements for 
	SNMP time stamp in tens of milliseconds.

  PreCondition:
  	None
 
  parameters:
  	None
 
  Return Values:
  	timeStamp - SYS_TICK timevalue
 
  Remarks:
 	None.
 ********************************************************************/
static SYS_TICK SNMPGetTimeStamp(void)
{
    SYS_TICK    timeStamp;
    timeStamp = (SYS_TICK_Get() * 100ull)/SYS_TICK_TicksPerSecondGet();

    return timeStamp;

}
コード例 #4
0
/*****************************************************************************
  Function:
	uint32_t BerkeleySNTPGetUTCSeconds(void)

  Summary:
	Obtains the current time from the SNTP module.

  Description:
	This function obtains the current time as reported by the SNTP module.  
	Use this value for absolute time stamping.  The value returned is (by
	default) the number of seconds since 01-Jan-1970 00:00:00.

  Precondition:
	None

  Parameters:
	None

  Returns:
  	The number of seconds since the Epoch.  (Default 01-Jan-1970 00:00:00)
  	
  Remarks:
	Do not use this function for time difference measurements.  The Tick
	module is more appropriate for those requirements.
  ***************************************************************************/
uint32_t BerkeleySNTPGetUTCSeconds(void)
{
	SYS_TICK dwTickDelta;
	SYS_TICK dwTick;

	// Update the dwSNTPSeconds variable with the number of seconds 
	// that has elapsed
	dwTick = SYS_TICK_Get();
	dwTickDelta = dwTick - dwLastUpdateTick;
	while(dwTickDelta > SYS_TICK_TicksPerSecondGet())
	{
		dwSNTPSeconds++;
		dwTickDelta -= SYS_TICK_TicksPerSecondGet();
	}
	
	// Save the tick and residual fractional seconds for the next call
	dwLastUpdateTick = dwTick - dwTickDelta;

	return dwSNTPSeconds;
}
コード例 #5
0
ファイル: app.c プロジェクト: ctapang/v0_70_01b
void APP_Tasks( void )
{
    static SYS_TICK startTick = 0;
    static IPV4_ADDR dwLastIP[2] = { {-1}, {-1} };
    IPV4_ADDR           ipAddr;
    int i;

    switch(appData.state)
    {
        case APP_MOUNT_DISK:
            if(SYS_FS_Mount(SYS_FS_NVM_VOL, LOCAL_WEBSITE_PATH_FS, MPFS2, 0, NULL)  == 0)
            {
                SYS_CONSOLE_PRINT("SYS_Initialize: The %s File System is mounted.\r\n", SYS_FS_MPFS_STRING);
                appData.state = APP_TCPIP_TRANSACT;
            }
            else
            {
                //SYS_CONSOLE_Print("SYS_Initialize: Failed to mount the %s File System! \r\n", SYS_FS_MPFS_STRING);
                appData.state = APP_MOUNT_DISK;
            }
            break;

        case APP_TCPIP_TRANSACT:

            if (SYS_TICK_Get() - startTick >= SYS_TICK_TicksPerSecondGet() / 2ul)
            {
                startTick = SYS_TICK_Get();
                LEDstate ^= APP_USERIO_LED_ASSERTED;
                SYS_USERIO_SetLED(SYS_USERIO_LED_0, LEDstate);
            }

            // if the IP address of an interface has changed
            // display the new value on the system console
            nNets = TCPIP_STACK_NumberOfNetworksGet();

            for (i = 0; i < nNets; i++)
            {
                netH = TCPIP_STACK_IndexToNet(i);
                ipAddr.Val = TCPIP_STACK_NetAddress(netH);
                if(dwLastIP[i].Val != ipAddr.Val)
                {
                    dwLastIP[i].Val = ipAddr.Val;

                    SYS_CONSOLE_MESSAGE(TCPIP_STACK_NetNameGet(netH));
                    SYS_CONSOLE_MESSAGE(" IP Address: ");
                    SYS_CONSOLE_PRINT("%d.%d.%d.%d \r\n", ipAddr.v[0], ipAddr.v[1], ipAddr.v[2], ipAddr.v[3]);
                }
            }
            break;

         default:
            break;
    }
}
コード例 #6
0
ファイル: auto_ip.c プロジェクト: webgou/Equinox-Clock
/*****************************************************************************
  Function:
	void AutoIPConflict(NET_CONFIG* pConfig)

  Summary:
	Handles AutoIP address conflicts.

  Description:
	This function will change the state machine to handle AutoIP address
    conflicts.

  Precondition:
	None

  Parameters:
	pConfig - Interface to cause an AutoIP conflict for. 

  Returns:
	None
***************************************************************************/
void AutoIPConflict (NET_CONFIG* pConfig)
{
	LoadState(_TCPIPStackNetIx(pConfig));

    AutoIPClient.conflicts++;

    // State handler
    switch (AutoIPClient.smAUTOIPState)
    {
        // During configuration, if there is a conflict, immediately give
        // up the current address and select a new one.
        // If more than 10 conflicts have occured, limit the rate of
        // address retrys to 1 every 60 seconds.
        case SM_AUTOIP_INIT_RNG:
        case SM_AUTOIP_CHECK_ADDRESS:
        case SM_AUTOIP_SETUP_MESSAGE:
        case SM_AUTOIP_GRATUITOUS_ARP1:
        case SM_AUTOIP_GRATUITOUS_ARP2:
        case SM_AUTOIP_GRATUITOUS_ARP3:
        case SM_AUTOIP_DELAY:
            if (AutoIPClient.conflicts >= 10u)
                AutoIPClient.smAUTOIPState = SM_AUTOIP_RATE_LIMIT_SET;
            else
                AutoIPClient.smAUTOIPState = SM_AUTOIP_CHECK_ADDRESS;
            break;
        case SM_AUTOIP_RATE_LIMIT_SET:
        case SM_AUTOIP_RATE_LIMIT_WAIT:
        case SM_AUTOIP_DISABLED:
            AutoIPClient.conflicts--;
            break;
        // If there is a conflict while we have an address configured,
        // send a defense packet.  If more than one conflict occurs within
        // 10 seconds, claim a new address.
        case SM_AUTOIP_CONFIGURED:
        case SM_AUTOIP_DEFEND:
            if (AutoIPClient.gAutoIPConflictTimer != 0u)
            {
                if (SYS_TICK_Get() - AutoIPClient.gAutoIPConflictTimer < SYS_TICK_TicksPerSecondGet() * 10)
                {
                    AutoIPClient.smAUTOIPState = SM_AUTOIP_CHECK_ADDRESS;
                    return;;
                }
            }
            AutoIPClient.gAutoIPConflictTimer = SYS_TICK_Get();
            AutoIPClient.smAUTOIPState = SM_AUTOIP_DEFEND;
            break;

    }
}
コード例 #7
0
/*****************************************************************************
 * FUNCTION: RawSetIndex
 *
 * RETURNS: True is success, false if timed out, which means attempted to set
 *          raw index past end of raw window.  Not a problem as long as no read
 *          or write occurs.
 *
 * PARAMS:
 *      rawId - RAW ID
 *      index - desired index
 *
 *  NOTES: Sets the RAW index for the specified RAW engine.  If attempt to set RAW
 *         index outside boundaries of RAW window this function will time out.
 *****************************************************************************/
bool RawSetIndex(uint16_t rawId, uint16_t index)
{
    uint8_t regId;
    uint16_t regValue;
    SYS_TICK startTickCount;
    SYS_TICK maxAllowedTicks;

    // set the RAW index
    regId = (rawId==RAW_ID_0)?RAW_0_INDEX_REG:RAW_1_INDEX_REG;
    Write16BitWFRegister(regId, index);

    startTickCount = SYS_TICK_Get();
    maxAllowedTicks = SYS_TICK_TicksPerSecondGet() / 200;   /* 5ms */
    if(maxAllowedTicks == 0)
    {
        maxAllowedTicks++;  // at least one system tick
    }
    
    regId = (rawId==RAW_ID_0)?RAW_0_STATUS_REG:RAW_1_STATUS_REG;
    
    while (1)
    {
        regValue = Read16BitWFRegister(regId);
        if ((regValue & WF_RAW_STATUS_REG_BUSY_MASK) == 0)
        {
            return true;
        }
        
        /* if timed out then trying to set index past end of raw window, which is OK so long as the app */
        /* doesn't try to access it                                                                     */
        if (SYS_TICK_Get() - startTickCount >= maxAllowedTicks)
        {
            return false;  /* timed out waiting for Raw set index to complete */
        }    
    }
}
コード例 #8
0
/*********************************************************************
  Function:
  	bool SNMPGetVar(SNMP_ID var, SNMP_INDEX index,uint8_t* ref, SNMP_VAL* val)
                                   
  Summary:
  	Used to Get/collect OID variable information.

  Description:
 	This is a callback function called by SNMP module. SNMP user must 
 	implement this function in user application and provide appropriate
 	data when called.
   	
  PreCondition:
  	None
 
  parameters:
  	var		-	Variable id whose value is to be returned
    index   -	Index of variable that should be transferred
    ref     -   Variable reference used to transfer
              	multi-byte data
                It is always SNMP_START_OF_VAR when very
                first byte is requested.
                Otherwise, use this as a reference to
                keep track of multi-byte transfers.
    val     -	Pointer to up to 4 byte buffer.
                If var data type is uint8_t, transfer data
                  in val->byte
                If var data type is uint16_t, transfer data in
                  val->word
                If var data type is uint32_t, transfer data in
                  val->dword
                If var data type is IP_ADDRESS, transfer data
                  in val->v[] or val->dword
                If var data type is COUNTER32, TIME_TICKS or
                  GAUGE32, transfer data in val->dword
                If var data type is ASCII_STRING or OCTET_STRING
                  transfer data in val->byte using multi-byte
                  transfer mechanism.
 
  Return Values:
  	true	-	If a value exists for given variable at given index.
    false 	-	Otherwise.
 
  Remarks:
 	None.
 ********************************************************************/
bool SNMPGetVar(SNMP_ID var, SNMP_INDEX index, uint8_t* ref, SNMP_VAL* val)
{
    uint8_t myRef;
    uint32_t dw;

    int lcdSize = 16*2+1;
    char message[lcdSize];

    myRef = *ref;

    switch(var)
    {
    case SYS_UP_TIME:
    {
	 
        SYS_TICK dw10msTicks;
        dw10msTicks = (SYS_TICK_Get() * 100ull)/SYS_TICK_TicksPerSecondGet();

        val->dword = dw10msTicks;
        return true;
    }    

    case LED_D5:
        val->byte = LED2_IO;
        return true;

    case LED_D6:
        val->byte = LED1_IO;
        return true;

    case PUSH_BUTTON:
        // There is only one button - meaning only index of 0 is allowed.
        val->byte = BUTTON0_IO;
        return true;

    case ANALOG_POT0:
        val->word = atoi((char*)AN0String);
        return true;

    case TRAP_RECEIVER_ID:
        if ( index < trapInfo.Size )
        {
            val->byte = index;
            return true;
        }
        break;

    case TRAP_RECEIVER_ENABLED:
        if ( index < trapInfo.Size )
        {
            val->byte = trapInfo.table[index].Flags.bEnabled;
            return true;
        }
        break;

    case TRAP_RECEIVER_IP:
        if ( index < trapInfo.Size )
        {
            val->dword = trapInfo.table[index].IPAddress.Val;
            return true;
        }
        break;

    case TRAP_COMMUNITY:
        if ( index < trapInfo.Size )
        {
            if ( trapInfo.table[index].communityLen == 0u )
                *ref = SNMP_END_OF_VAR;
            else
            {
                val->byte = trapInfo.table[index].community[myRef];

                myRef++;

                if ( myRef == trapInfo.table[index].communityLen )
                    *ref = SNMP_END_OF_VAR;
                else
                    *ref = myRef;
            }
            return true;
        }
        break;

    case LCD_DISPLAY:
        break;
    }

    return false;
}
コード例 #9
0
/**************************************************************************
  Function:
 	void SNMPTrapDemo(void)
 
  Summary:	
  	Send trap pdu demo application.
 	  	  
  Description:		
	This routine sends a trap pdu for the predefined ip addresses with the
	agent. The "event" to generate this trap pdu is "BUTTON_PUSH_EVENT". Whenever
	there occurs a specific button push, this routine is called and sends
	a trap containing PUSH_BUTTON mib var OID and notification type 
	as authentication failure. 
       
  PreCondition:
 	Application defined event occurs to send the trap.
 	
  parameters:
     None.
 
  Returns:          
 	 None.
 
  Remarks:
    This routine guides how to build a event generated trap notification.
    The application should make use of SNMPSendTrap() routine to generate 
    and send trap.
 *************************************************************************/
void SNMPTrapDemo(void)
{
	static SYS_TICK TimerRead=0;
	static bool analogPotNotify = false,buttonPushNotify=false;
	static uint8_t anaPotNotfyCntr=0,buttonPushNotfyCntr=0;
	static SNMP_VAL buttonPushval,analogPotVal;
	static uint8_t potReadLock=false,buttonLock=false;
	static uint8_t timeLock=false;
	static uint8_t maxTryToSendTrap=0;
	
	if(timeLock==(uint8_t)false)
	{
		TimerRead=SYS_TICK_Get();
		timeLock=true;
	}

	#if 1
	if(anaPotNotfyCntr >= trapInfo.Size)
	{
		anaPotNotfyCntr = 0;
		potReadLock=false;
		//analogPotNotify = false;
		analogPotNotify = true;
	}
	#endif
	
	if(!analogPotNotify)
	{
		//Read POT reading once and send trap to all configured recipient
		if(potReadLock ==(uint8_t)false)
		{
            analogPotVal.word= (uint16_t)ADC1BUF0;
			
			//Avoids Reading POT for every iteration unless trap sent to each configured recipients 
			potReadLock=true; 
		}
		if(trapInfo.table[anaPotNotfyCntr].Flags.bEnabled)
		{
			if(analogPotVal.word >512u)
			{
				gSpecificTrapNotification=POT_READING_MORE_512;
				gGenericTrapNotification=ENTERPRISE_SPECIFIC;
				if(SendNotification(anaPotNotfyCntr, ANALOG_POT0, analogPotVal))
					anaPotNotfyCntr++;
				else
				{					
					if(maxTryToSendTrap>=MAX_TRY_TO_SEND_TRAP)
					{
						anaPotNotfyCntr++;
						maxTryToSendTrap = 0;
						return;
					}
					maxTryToSendTrap++;
					return ;
				}
			}
		}
		else
			anaPotNotfyCntr++;
			
	}


	if(buttonPushNotfyCntr==trapInfo.Size)
	{
		buttonPushNotfyCntr = 0;
		buttonLock=false;
		buttonPushNotify = false;
	}


	if(buttonLock == (uint8_t)false)
	{
		if(BUTTON3_IO == 0u)
		{
			buttonPushNotify = true;
			buttonLock =true;
		}
	}

	if(buttonPushNotify)
	{			  
		buttonPushval.byte = 0;
		if ( trapInfo.table[buttonPushNotfyCntr].Flags.bEnabled )
		{
			gSpecificTrapNotification=BUTTON_PUSH_EVENT;
			gGenericTrapNotification=ENTERPRISE_SPECIFIC;
			if(SendNotification(buttonPushNotfyCntr, PUSH_BUTTON, buttonPushval))
				buttonPushNotfyCntr++;
		}
		else
			buttonPushNotfyCntr++;
	}

	//Try for max 5 seconds to send TRAP, do not get block in while()
	if((SYS_TICK_Get()-TimerRead)>(5*SYS_TICK_TicksPerSecondGet()))
	{
		UDPDiscard(s, gpSnmpIf);    
		buttonPushNotfyCntr = 0;
		buttonLock=false;
		buttonPushNotify = false;
		anaPotNotfyCntr = 0;
		potReadLock=false;
		analogPotNotify = false;
		timeLock=false;
		gSpecificTrapNotification=VENDOR_TRAP_DEFAULT;
		gGenericTrapNotification=ENTERPRISE_SPECIFIC;
		return;
	}

}
コード例 #10
0
/**************************************************************************
  Function:
 	void SNMPSendTrap(void)
 
  Summary:	
  	 Prepare, validate remote node which will receive trap and send trap pdu.
 	 	  
  Description:		
     This function is used to send trap notification to previously 
     configured ip address if trap notification is enabled. There are
     different trap notification code. The current implementation
     sends trap for authentication failure (4).
  
  PreCondition:
 	 If application defined event occurs to send the trap.
 
  parameters:
     None.
 
  Returns:          
 	 None.
 
  Remarks:
     This is a callback function called by the application on certain 
     predefined events. This routine only implemented to send a 
     authentication failure Notification-type macro with PUSH_BUTTON
     oid stored in MPFS. If the ARP is no resolved i.e. if 
     SNMPIsNotifyReady() returns false, this routine times 
     out in 5 seconds. This routine should be modified according to 
     event occured and should update corrsponding OID and notification
     type to the trap pdu.
 *************************************************************************/
void SNMPSendTrap(void)
{
	static uint8_t timeLock=false;
	static uint8_t receiverIndex=0; ///is application specific
	IP_ADDR remHostIPAddress,* remHostIpAddrPtr;
	SNMP_VAL val;
	static SYS_TICK TimerRead;
    
	static enum 
	{
		SM_PREPARE,
		SM_NOTIFY_WAIT 
	} smState = SM_PREPARE;

    gpSnmpIf = TCPIP_STACK_GetDefaultNet();

	if(trapInfo.table[receiverIndex].Flags.bEnabled)
	{
		remHostIPAddress.v[0] = trapInfo.table[receiverIndex].IPAddress.v[3];
		remHostIPAddress.v[1] = trapInfo.table[receiverIndex].IPAddress.v[2];
		remHostIPAddress.v[2] = trapInfo.table[receiverIndex].IPAddress.v[1];
		remHostIPAddress.v[3] = trapInfo.table[receiverIndex].IPAddress.v[0];
		remHostIpAddrPtr = &remHostIPAddress;
		if(timeLock==(uint8_t)false)
		{
			TimerRead=SYS_TICK_Get();
			timeLock=true;
		}
	}	
	else
	{
		receiverIndex++;
		if((receiverIndex == (uint8_t)TRAP_TABLE_SIZE))
		{
			receiverIndex=0;
			timeLock=false;
			gSendTrapFlag=false;	
			UDPDiscard(s, gpSnmpIf);
		}
		return;
		
	}
		
	switch(smState)
	{
	
		case SM_PREPARE:

			SNMPNotifyPrepare(remHostIpAddrPtr,trapInfo.table[receiverIndex].community,
						trapInfo.table[receiverIndex].communityLen,
						MICROCHIP,			  // Agent ID Var
						gSpecificTrapNotification,					  // Notification code.
						SNMPGetTimeStamp());
			smState++;
			break;
			
		case SM_NOTIFY_WAIT:
			if(SNMPIsNotifyReady(remHostIpAddrPtr))
			{
				smState = SM_PREPARE;
		 		val.byte = 0;
				receiverIndex++;

				//application has to decide on which SNMP var OID to send. Ex. PUSH_BUTTON	
				SNMPNotify(gOIDCorrespondingSnmpMibID, val, 0);
            	smState = SM_PREPARE;
				UDPDiscard(s, gpSnmpIf);
				break;
			}
	}	
		
	//Try for max 5 seconds to send TRAP, do not get block in while()
	if((SYS_TICK_Get()-TimerRead)>(5*SYS_TICK_TicksPerSecondGet())|| (receiverIndex == (uint8_t)TRAP_TABLE_SIZE))
	{
		UDPDiscard(s, gpSnmpIf);
		smState = SM_PREPARE;
		receiverIndex=0;
		timeLock=false;
		gSendTrapFlag=false;
		return;
	}

}
コード例 #11
0
static int WFEasyConfigProcess(TCPIP_NET_IF* pNetIf)
{
#if 0  // should not be needed
    uint8_t ConnectionState;
#endif
    t_securityContext securityContext;
    
    #if defined (EZ_CONFIG_STALL)
        if (CFGCXT.cfg_state == cfg_stopped)
        {
            /* State machine just started get current time stamp */
            CFGCXT.cfg_state = cfg_stalled;
            CFGCXT.timeStart = SYS_TICK_Get();
            return false;
        }

        /* Wait for stall time to expire */
        if (CFGCXT.cfg_state == cfg_stalled)
        {
            SYS_TICK time = SYS_TICK_Get();
            if ((time - CFGCXT.timeStart) < (WF_EASY_CONFIG_DELAY_TIME * SYS_TICK_TicksPerSecondGet()))
            {
                return false;
            }
        }
    #endif //EZ_CONFIG_STALL

#if 0  // should not be needed
    /* We will re-use the current profile */
    WF_ConnectionStateGet(&ConnectionState);
#endif

    /* Need to disconnect */
    WF_Disconnect();

    /* Set SSID... */
    if (CFGCXT.ssid)
    {
        WF_SsidSet(CFGCXT.ssid, strlen((char*)CFGCXT.ssid));
    }

    /* Now deal with security... */
    switch ((uint8_t)CFGCXT.security)
    {
        case WF_SECURITY_OPEN: /* No security */
            WF_SecurityOpenSet();
            break; 

        case WF_SECURITY_WPA_AUTO_WITH_PASS_PHRASE:
            if (CFGCXT.key)
            {
                securityContext.wpaContext.wpaSecurityType = WF_SECURITY_WPA_AUTO_WITH_PASS_PHRASE;
                securityContext.wpaContext.keyInfo.keyLength = strlen((char *)CFGCXT.key);
                memcpy(securityContext.wpaContext.keyInfo.key, CFGCXT.key, securityContext.wpaContext.keyInfo.keyLength);
                WF_SecurityWpaSet(&securityContext.wpaContext);
            }
            break;

        case WF_SECURITY_WPA_AUTO_WITH_KEY:
            if (CFGCXT.key) 
            {
                securityContext.wpaContext.wpaSecurityType = WF_SECURITY_WPA_AUTO_WITH_KEY;
                securityContext.wpaContext.keyInfo.keyLength = 32;
                memcpy(securityContext.wpaContext.keyInfo.key, CFGCXT.key, 32);
                WF_SecurityWpaSet(&securityContext.wpaContext);
            }
            break;

        case WF_SECURITY_WEP_40:
            if (CFGCXT.key)
            {
                securityContext.wepContext.wepSecurityType = WF_SECURITY_WEP_40;
                securityContext.wepContext.wepKeyLength    = WF_WEP40_KEY_LENGTH;
                memset(CFGCXT.key, 0x00, WF_WEP40_KEY_LENGTH);
                memset(securityContext.wepContext.wepKey, 0x00, WF_WEP40_KEY_LENGTH);
                securityContext.wepContext.wepKeyType      = WF_SECURITY_WEP_OPENKEY;
                WF_SecurityWepSet(&securityContext.wepContext);
            }
            break;

        case WF_SECURITY_WEP_104:
            if (CFGCXT.key)
            {
                securityContext.wepContext.wepSecurityType = WF_SECURITY_WEP_104;
                securityContext.wepContext.wepKeyLength    = WF_WEP104_KEY_LENGTH;
                memset(CFGCXT.key, 0x00, WF_WEP104_KEY_LENGTH);
                memset(securityContext.wepContext.wepKey, 0x00, WF_WEP104_KEY_LENGTH);
                securityContext.wepContext.wepKeyType      = WF_SECURITY_WEP_OPENKEY;
                WF_SecurityWepSet(&securityContext.wepContext);
            }
            break;
    }
 
    #if defined (EZ_CONFIG_STORE) && defined(TCPIP_STACK_USE_STORAGE)
        #if 0
            TCPIP_STORAGE_HANDLE hS;
            hS = TCPIPStorageOpen(0, 1);
            TCPIPStorageSaveIfConfig(hS, "MRF24W", true);
            TCPIPStorageClose(hS);
        #else
            WF_ConfigDataSave();
        #endif
    #endif // defined (EZ_CONFIG_STORE)

    /* Set wlan mode */
    WF_NetworkTypeSet(CFGCXT.type);

#if defined(DISABLE_MODULE_FW_CONNECT_MANAGER_IN_INFRASTRUCTURE)
    WF_ReconnectModeSet(0,                                  // report-only when connection lost (no reconnect)
                        WF_DO_NOT_ATTEMPT_TO_RECONNECT,     // report-only when deauth received (no reconnect)
                        40,                                 // set beacon timeout to 40 beacon periods
                        WF_DO_NOT_ATTEMPT_TO_RECONNECT);    // report only when beacon timeout occurs
#endif
    //TCPIP_NET_IF* p_config= (TCPIP_NET_IF*)GetNetworkConfig();
    if (p_wifi_ConfigData->networkType == WF_NETWORK_TYPE_INFRASTRUCTURE)
    {
        WF_ReconnectModeSet(WF_RETRY_FOREVER,           // retry forever to connect to WiFi network
                            WF_ATTEMPT_TO_RECONNECT,    // reconnect on deauth from AP
                            40,                         // beacon timeout is 40 beacon periods
                            WF_ATTEMPT_TO_RECONNECT);   // reconnect on beacon timeout
    }

#if WF_DEFAULT_NETWORK_TYPE == WF_NETWORK_TYPE_SOFT_AP
    // SoftAP: To allow redirection, need to hibernate before changing network type. Module
    //         FW has SoftAP flag and therefore hibernate mode is needed to clear this
    //         indication and allow proper network change. This should work for non-SoftAP,
    //         but these have not been tested yet.
    #if 0
        WF_hibernate.state = WF_HB_ENTER_SLEEP;
        WF_hibernate.wakeup_notice = false;
        //WFConsolePrintRomStr("SoftAP redirection: Put Wi-Fi module into hibernate mode.", true);

        DelayMs(200);

        WF_hibernate.wakeup_notice = true;
        //WFConsolePrintRomStr("Wakeup Wi-Fi module.", true);
    #else
        extern bool SoftAP_Redirection_Enable;
        SoftAP_Redirection_Enable = true;
    #endif
#else
    /* Kick off connection now... */
    WF_Connect();
    #if defined(TCPIP_STACK_USE_EVENT_NOTIFICATION)
        WifiAsyncSetEventPending(ASYNC_DHCP_CONFIG_PENDING); // configure DHCP after init complete
    #endif
#endif
    /* Change state and return true to show we are done! */
    CFGCXT.cfg_state = cfg_stopped;

    return true;
}
コード例 #12
0
/**************************************************************************
  Function:
 	void SNMPV2TrapDemo(void)
 
  Summary:	
  	Send SNMP V2 notification with multiple varbinds.
 	  	  
  Description:		
	This routine sends a trap v2 pdu with multiple varbind variables
	for the predefined ip addresses with the agent. And as per RFC1905 
	the first two variable bindings in the varbind pdu list of an
   	SNMPv2-Trap-PDU are sysUpTime.0 and snmpTrapOID.0 respectively.
   	To support multiple varbind, user need to call SendNotification()
    for the first varbind variable and SendNotification() will do the 
    arp resolve and adds sysUpTime.0 and snmpTrapOID.0 variable to 
    the pdu. For the second varbind variable onwards user need to 
   	call only SNMPNotify().
	In this demo , snmpv2 trap includes ANALOG_POT0,PUSH_BUTTON and LED_D5
	variable bindains and this trap can be generated by using portmeter value.
	and SNMPv2-Trap-PDU will be generated only when pot meter reading exceeds 501.
	
	gSetTrapSendFlag Should be set to true when user is trying to send first 
	variable binding and gSetTrapSendFlag should be set to false before 
    sending the last variable binding.

	* if user is sending only one variable binding then 
	* gSetTrapSendFlag should be set to False.	
    * user can add more variable bindings.
  PreCondition:
 	Application defined event occurs to send the trap.
 	
  parameters:
     None.
 
  Returns:          
 	 None.
 
  Remarks:
    This routine guides how to build a event generated trap notification.
 *************************************************************************/
void SNMPV2TrapDemo(void)
{
	static SYS_TICK tempTimerRead = 0;
	static uint8_t	trapIndex=0;
	static SNMP_VAL		analogPotVal;
	static uint8_t potReadLock = false;
	static uint8_t timeLock = false;
	static uint8_t maxTryToSendTrap=0;
	
	if(timeLock==(uint8_t)false)
	{
		tempTimerRead=SYS_TICK_Get();
		timeLock=true;
	}

    gpSnmpIf = TCPIP_STACK_GetDefaultNet();

	for(;trapIndex<TRAP_TABLE_SIZE;trapIndex++)
	{	
		if(!trapInfo.table[trapIndex].Flags.bEnabled)
			continue;
		
		//Read POT reading once and send trap to all configured recipient
		if(potReadLock ==(uint8_t)false)
		{
			analogPotVal.word= (uint16_t)ADC1BUF0;
			potReadLock    = true;
		}
	
		if(analogPotVal.word >512u)
		{
			/*
			 * prepare  and send multivarbind pdu using pot meter value. 
			 * for SNMP v2 trap sysUpTime.0 and SNMPv2TrapOID.0 are mandatory
			 * apart from these varbinds, push button and potmeter OID are included
			 * to this pdu.
			*/
			gSpecificTrapNotification = 1; //expecting 1 should be the specific trap.
			gGenericTrapNotification = ENTERPRISE_SPECIFIC;
			gSetTrapSendFlag = true;
			// insert ANALOG_POT0 OID value and OID to the varbind pdu
			//set global flag gSetTrapSendFlag to true , it signifies that there are more than one 
			// variable need to be the part of SNMP v2 TRAP. 
			// if there is  only varbind variable to be the part of SNMP v2 trap, 
			// then user should set gSetTrapSendFlag to false.
			//gSetTrapSendFlag = false;

			if(SendNotification(trapIndex,ANALOG_POT0,analogPotVal) == false)
			{
				if(maxTryToSendTrap >= MAX_TRY_TO_SEND_TRAP)
				{
					trapIndex++;
					maxTryToSendTrap = 0;
					return;
				}
				maxTryToSendTrap++;
				return ;
			}
			//prepare PUSH_BUTTON trap .for the next trap varbind we need to use snmp_notify instead of 
			// SendNotification(), because we have already prepared SNMP v2 trap header 
			//and arp has been resolved already.
			
			analogPotVal.byte = BUTTON0_IO;
			SNMPNotify(PUSH_BUTTON,analogPotVal,0);
		
			// if this is the last trap variable need to be the part of SNMP v2 Trap,
			// then we should disable gSetTrapSendFlag to false
			gSetTrapSendFlag = false;
			analogPotVal.byte = LED0_IO;
			SNMPNotify(LED_D5,analogPotVal,0);			
		}
	}

	//Try for max 5 seconds to send TRAP, do not get block in while()
	if((SYS_TICK_Get()-tempTimerRead)>(5*SYS_TICK_TicksPerSecondGet()))
	{
//		UDPDiscard(s, gpSnmpIf);
		potReadLock = false;
		timeLock = false;
		trapIndex = 0;
		analogPotVal.word = 0;
		return;
	}
}
コード例 #13
0
/*****************************************************************************
  Function:
	void DNSClientTask(void)

  Summary:
	DNS client state machine
	
  Description:
    Process the DNS client state machine
  
  Precondition:
	DNSClientInit has been called.

  Parameters:
    None
    
  Return Values:
    None

  ***************************************************************************/
void DNSClientTask(void)
{
	uint8_t 				i;
	TCPIP_UINT16_VAL			w;
	DNS_HEADER			DNSHeader;
	DNS_ANSWER_HEADER	DNSAnswerHeader;
    

    switch(smDNS)
	{
		case DNS_IDLE:
            break;  // nothing to do

		case DNS_START:
            smDNS = DNSRetry(DNS_START);
            stateStartTime = 0;  // flag the first Open try
			break;

		case DNS_OPEN_SOCKET:
            DNSSocket = UDPOpenClient(IP_ADDRESS_TYPE_IPV4, DNS_CLIENT_PORT, (IP_MULTI_ADDRESS*)(DNSServers + vDNSServerIx));
			if(DNSSocket == INVALID_UDP_SOCKET)
            {
                if(stateStartTime == 0)
                {
                    stateStartTime = SYS_TICK_Get();
                }
                else if(SYS_TICK_Get() - stateStartTime > (DNS_CLIENT_OPEN_TMO * SYS_TICK_TicksPerSecondGet()))
                {
					smDNS = DNS_FAIL_OPEN_TMO;
                }
                
                break;
            }
            
            // got a valid UDP socket
            UDPSocketSetNet(DNSSocket, pDNSNet);
            stateStartTime = SYS_TICK_Get();
            smDNS = DNS_QUERY;
            // no break, start sending the query;

		case DNS_QUERY:
            if(!UDPIsOpened(DNSSocket) || (UDPIsTxPutReady(DNSSocket, 18 + strlen (DNSHostName)) < (18 + strlen (DNSHostName))))
            {
                if(SYS_TICK_Get() - stateStartTime > (DNS_CLIENT_OPEN_TMO * SYS_TICK_TicksPerSecondGet()))
                {
					smDNS = DNS_FAIL_OPEN_TMO;
                }
                
				break;  // wait some more
            }
			
			// Put DNS query here
			SentTransactionID.Val = (uint16_t)rand();
			UDPPut(DNSSocket, SentTransactionID.v[1]);// User chosen transaction ID
			UDPPut(DNSSocket, SentTransactionID.v[0]);
			UDPPut(DNSSocket, 0x01);		// Standard query with recursion
			UDPPut(DNSSocket, 0x00);	
			UDPPut(DNSSocket, 0x00);		// 0x0001 questions
			UDPPut(DNSSocket, 0x01);
			UDPPut(DNSSocket, 0x00);		// 0x0000 answers
			UDPPut(DNSSocket, 0x00);
			UDPPut(DNSSocket, 0x00);		// 0x0000 name server resource records
			UDPPut(DNSSocket, 0x00);
			UDPPut(DNSSocket, 0x00);		// 0x0000 additional records
			UDPPut(DNSSocket, 0x00);

			// Put hostname string to resolve
            DNSPutString(DNSSocket, DNSHostName);

			UDPPut(DNSSocket, 0x00);		// Type: DNS_TYPE_A A (host address) or DNS_TYPE_MX for mail exchange
			UDPPut(DNSSocket, RecordType);
			UDPPut(DNSSocket, 0x00);		// Class: IN (Internet)
			UDPPut(DNSSocket, 0x01);

			UDPFlush(DNSSocket);
			stateStartTime = SYS_TICK_Get();
			smDNS = DNS_GET_RESULT;
			break;

		case DNS_GET_RESULT:
			if(!UDPIsGetReady(DNSSocket))
			{
				if(SYS_TICK_Get() - stateStartTime > (DNS_CLIENT_SERVER_TMO * SYS_TICK_TicksPerSecondGet()))
                {
					smDNS = DNS_FAIL_SERVER;
                }
				break;
			}


			// Retrieve the DNS header and de-big-endian it
			UDPGet(DNSSocket, &DNSHeader.TransactionID.v[1]);
			UDPGet(DNSSocket, &DNSHeader.TransactionID.v[0]);

			// Throw this packet away if it isn't in response to our last query
			if(DNSHeader.TransactionID.Val != SentTransactionID.Val)
			{
				UDPDiscard(DNSSocket);
				break;
			}

			UDPGet(DNSSocket, &DNSHeader.Flags.v[1]);
			UDPGet(DNSSocket, &DNSHeader.Flags.v[0]);
			UDPGet(DNSSocket, &DNSHeader.Questions.v[1]);
			UDPGet(DNSSocket, &DNSHeader.Questions.v[0]);
			UDPGet(DNSSocket, &DNSHeader.Answers.v[1]);
			UDPGet(DNSSocket, &DNSHeader.Answers.v[0]);
			UDPGet(DNSSocket, &DNSHeader.AuthoritativeRecords.v[1]);
			UDPGet(DNSSocket, &DNSHeader.AuthoritativeRecords.v[0]);
			UDPGet(DNSSocket, &DNSHeader.AdditionalRecords.v[1]);
			UDPGet(DNSSocket, &DNSHeader.AdditionalRecords.v[0]);

			// Remove all questions (queries)
			while(DNSHeader.Questions.Val--)
			{
				DNSDiscardName(DNSSocket);
				UDPGet(DNSSocket, &w.v[1]);		// Question type
				UDPGet(DNSSocket, &w.v[0]);
				UDPGet(DNSSocket, &w.v[1]);		// Question class
				UDPGet(DNSSocket, &w.v[0]);
			}
			
			// Scan through answers
			while(DNSHeader.Answers.Val--)
			{				
				DNSDiscardName(DNSSocket);					// Throw away response name
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseType.v[1]);		// Response type
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseType.v[0]);
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseClass.v[1]);	// Response class
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseClass.v[0]);
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseTTL.v[3]);		// Time to live
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseTTL.v[2]);
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseTTL.v[1]);
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseTTL.v[0]);
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseLen.v[1]);		// Response length
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseLen.v[0]);

				// Make sure that this is a 4 byte IP address, response type A or MX, class 1
				// Check if this is Type A, MX, or AAAA
				if( DNSAnswerHeader.ResponseClass.Val	== 0x0001u) // Internet class
				{
                    if (DNSAnswerHeader.ResponseType.Val	== 0x0001u &&
    					DNSAnswerHeader.ResponseLen.Val		== 0x0004u)
                    {
    					Flags.bits.AddressValid = true;
                        Flags.bits.AddressType = IP_ADDRESS_TYPE_IPV4;
    					UDPGet(DNSSocket, &ResolvedAddress.ipv4Address.v[0]);
    					UDPGet(DNSSocket, &ResolvedAddress.ipv4Address.v[1]);
    					UDPGet(DNSSocket, &ResolvedAddress.ipv4Address.v[2]);
    					UDPGet(DNSSocket, &ResolvedAddress.ipv4Address.v[3]);
    					goto DoneSearchingRecords;
                    }
                    else if (DNSAnswerHeader.ResponseType.Val == 0x001Cu &&
    					        DNSAnswerHeader.ResponseLen.Val	== 0x0010u)
                    {
                        if (RecordType != DNS_TYPE_AAAA)
                        {
        					while(DNSAnswerHeader.ResponseLen.Val--)
        					{
        						UDPGet(DNSSocket, &i);
        					}
                            break;
                        }
    					Flags.bits.AddressValid = true;
                        Flags.bits.AddressType = IP_ADDRESS_TYPE_IPV6;
                        UDPGetArray (DNSSocket, (void *)&ResolvedAddress.ipv6Address, sizeof (IPV6_ADDR));
    					goto DoneSearchingRecords;                        
                    }
                    else
                    {
    					while(DNSAnswerHeader.ResponseLen.Val--)
    					{
    						UDPGet(DNSSocket, &i);
    					}
                    }
				}
				else
				{
					while(DNSAnswerHeader.ResponseLen.Val--)
					{
						UDPGet(DNSSocket, &i);
					}
				}
			}

			// Remove all Authoritative Records
			while(DNSHeader.AuthoritativeRecords.Val--)
			{
				DNSDiscardName(DNSSocket);					// Throw away response name
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseType.v[1]);		// Response type
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseType.v[0]);
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseClass.v[1]);	// Response class
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseClass.v[0]);
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseTTL.v[3]);		// Time to live
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseTTL.v[2]);
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseTTL.v[1]);
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseTTL.v[0]);
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseLen.v[1]);		// Response length
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseLen.v[0]);

				// Make sure that this is a 4 byte IP address, response type A or MX, class 1
				// Check if this is Type A
				if( DNSAnswerHeader.ResponseClass.Val	== 0x0001u) // Internet class
				{
                    if (DNSAnswerHeader.ResponseType.Val	== 0x0001u &&
    					DNSAnswerHeader.ResponseLen.Val		== 0x0004u)
                    {
    					Flags.bits.AddressValid = true;
                        Flags.bits.AddressType = IP_ADDRESS_TYPE_IPV4;
    					UDPGet(DNSSocket, &ResolvedAddress.ipv4Address.v[0]);
    					UDPGet(DNSSocket, &ResolvedAddress.ipv4Address.v[1]);
    					UDPGet(DNSSocket, &ResolvedAddress.ipv4Address.v[2]);
    					UDPGet(DNSSocket, &ResolvedAddress.ipv4Address.v[3]);
    					goto DoneSearchingRecords;
                    }
                    else if (DNSAnswerHeader.ResponseType.Val == 0x001Cu &&
    					        DNSAnswerHeader.ResponseLen.Val	== 0x0010u)
                    {
                        if (RecordType != DNS_TYPE_AAAA)
                        {
        					while(DNSAnswerHeader.ResponseLen.Val--)
        					{
        						UDPGet(DNSSocket, &i);
        					}
                            break;
                        }
    					Flags.bits.AddressValid = true;
                        Flags.bits.AddressType = IP_ADDRESS_TYPE_IPV6;
                        UDPGetArray (DNSSocket, (void *)&ResolvedAddress.ipv6Address, sizeof (IPV6_ADDR));
    					goto DoneSearchingRecords;                        
                    }
                    else
                    {
    					while(DNSAnswerHeader.ResponseLen.Val--)
    					{
    						UDPGet(DNSSocket, &i);
    					}
                    }
				}
				else
				{
					while(DNSAnswerHeader.ResponseLen.Val--)
					{
						UDPGet(DNSSocket, &i);
					}
				}
			}

			// Remove all Additional Records
			while(DNSHeader.AdditionalRecords.Val--)
			{
				DNSDiscardName(DNSSocket);					// Throw away response name
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseType.v[1]);		// Response type
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseType.v[0]);
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseClass.v[1]);	// Response class
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseClass.v[0]);
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseTTL.v[3]);		// Time to live
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseTTL.v[2]);
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseTTL.v[1]);
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseTTL.v[0]);
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseLen.v[1]);		// Response length
				UDPGet(DNSSocket, &DNSAnswerHeader.ResponseLen.v[0]);

				// Make sure that this is a 4 byte IP address, response type A or MX, class 1
				// Check if this is Type A
				if( DNSAnswerHeader.ResponseClass.Val	== 0x0001u) // Internet class
				{
                    if (DNSAnswerHeader.ResponseType.Val	== 0x0001u &&
    					DNSAnswerHeader.ResponseLen.Val		== 0x0004u)
                    {
    					Flags.bits.AddressValid = true;
                        Flags.bits.AddressType = IP_ADDRESS_TYPE_IPV4;
    					UDPGet(DNSSocket, &ResolvedAddress.ipv4Address.v[0]);
    					UDPGet(DNSSocket, &ResolvedAddress.ipv4Address.v[1]);
    					UDPGet(DNSSocket, &ResolvedAddress.ipv4Address.v[2]);
    					UDPGet(DNSSocket, &ResolvedAddress.ipv4Address.v[3]);
    					goto DoneSearchingRecords;
                    }
                    else if (DNSAnswerHeader.ResponseType.Val == 0x001Cu &&
    					        DNSAnswerHeader.ResponseLen.Val	== 0x0010u)
                    {
                        if (RecordType != DNS_TYPE_AAAA)
                        {
        					while(DNSAnswerHeader.ResponseLen.Val--)
        					{
        						UDPGet(DNSSocket, &i);
        					}
                            break;
                        }
    					Flags.bits.AddressValid = true;
                        Flags.bits.AddressType = IP_ADDRESS_TYPE_IPV6;
                        UDPGetArray (DNSSocket, (void *)&ResolvedAddress.ipv6Address, sizeof (IPV6_ADDR));
    					goto DoneSearchingRecords;                        
                    }
                    else
                    {
    					while(DNSAnswerHeader.ResponseLen.Val--)
    					{
    						UDPGet(DNSSocket, &i);
    					}
                    }
				}
				else
				{
					while(DNSAnswerHeader.ResponseLen.Val--)
					{
						UDPGet(DNSSocket, &i);
					}
				}
			}

DoneSearchingRecords:

			UDPDiscard(DNSSocket);
            _DNSReleaseSocket();
			if(Flags.bits.AddressValid)
            {
                smDNS = DNS_DONE;
            }
            else
            {
                smDNS = DNSRetry(DNS_FAIL_SERVER);
            }
            break;  // done
            
		case DNS_FAIL_ARP:
            // see if there is other server we may try
            smDNS = DNSRetry(DNS_FAIL_ARP);
            break;

		case DNS_FAIL_SERVER:
            smDNS = DNSRetry(DNS_FAIL_SERVER);
			break;

        default:    // DNS_DONE, DNS_FAIL_ARP_TMO, DNS_FAIL_OPEN_TMO, DNS_FAIL_SERVER_TMO  
            // either done or some error state
            break;
	}
    
#if DNS_CLIENT_VERSION_NO >= 2
    dnsTickPending = 0;
#endif  // DNS_CLIENT_VERSION_NO >= 2
}
コード例 #14
0
/*****************************************************************************
  Function:
	void UDPPerformanceTask(NET_CONFIG* pConfig)

  Summary:
	Tests the transmit performance of the UDP module.

  Description:
	This function tests the transmit performance of the UDP module.  At boot,
	this module will transmit 1024 large UDP broadcast packets of 1024 bytes
	each.  Using a packet sniffer, one can determine how long this process 
	takes and calculate the transmit rate of the stack.  This function tests 
	true UDP performance in that it will open a socket, transmit one packet, 
	and close the socket for each loop.  After this initial transmission, the
	module can be re-enabled by holding button 3.
	
	This function is particularly useful after development to determine the
	impact of your application code on the stack's performance.  A before and
	after comparison will indicate if your application is unacceptably
	blocking the processor or taking too long to execute.

  Precondition:
	UDP is initialized.

  Parameters:
	pConfig - network to run on

  Returns:
	None
  ***************************************************************************/
void UDPPerformanceTask(NET_CONFIG* pConfig)
{
	UDP_SOCKET	MySocket;
	NODE_INFO	Remote;
	uint16_t		wTemp;
	static uint32_t dwCounter = 1;

	if((BUTTON3_IO) && (dwCounter > 1024u))
		return;

	// Suppress transmissions if we don't have an Ethernet link so our counter starts correctly at 0x00000001
	if(!MACIsLinked(_TCPIPStackNetToMac(pConfig)))
		return;
	
	#if defined(TCPIP_STACK_USE_DHCP_CLIENT) && defined(DELAY_UDP_PERFORMANCE_TEST)
	{
		static SYS_TICK dwTimer = 0;
		
		// Wait until DHCP module is finished
		if(!DHCPIsBound(pConfig))
		{
			dwTimer = SYS_TICK_Get();
			return;
		}

		// Wait an additional half second after DHCP is finished to let the announce module and any other stack state machines to reach normal operation
		if(SYS_TICK_Get() - dwTimer < SYS_TICK_TicksPerSecondGet()/2)
			return;
	}
	#endif

	// Set the socket's destination to be a broadcast over our IP 
	// subnet
	// Set the MAC destination to be a broadcast
	memset(&Remote, 0xFF, sizeof(Remote));
	
	// Open a UDP socket for outbound transmission
	MySocket = UDPOpen((uint32_t)&Remote,UDP_OPEN_NODE_INFO,0,PERFORMANCE_PORT);
	
	// Abort operation if no UDP sockets are available
	// If this ever happens, incrementing UDP_MAX_SOCKETS in 
	// udp_config.h may help (at the expense of more global memory 
	// resources).
	if(MySocket == INVALID_UDP_SOCKET)
		return;
    UDPSocketSetNet(MySocket, pConfig);

	// Make certain the socket can be written to
	if(!UDPIsPutReady(MySocket))
	{
		UDPClose(MySocket);
		return;
	}
	
	// Put counter value into first 4 bytes of the packet
	UDPPutArray(MySocket, (uint8_t*)&dwCounter, sizeof(dwCounter));
	dwCounter++;
	
	wTemp = UDPPutArray(MySocket, (const uint8_t*)
			"The quick brown fox tried to jump over the yellow dog.  Unfortunately, the yellow dog stood up while the fox was in mid-jump.  As a result, the two collided.  Then, the dog, being the omnivore that it is, ate the quick brown fox.  This line is 256 bytes.\r\n"
			"The quick brown fox tried to jump over the yellow dog.  Unfortunately, the yellow dog stood up while the fox was in mid-jump.  As a result, the two collided.  Then, the dog, being the omnivore that it is, ate the quick brown fox.  This line is 256 bytes.\r\n"
			"The quick brown fox tried to jump over the yellow dog.  Unfortunately, the yellow dog stood up while the fox was in mid-jump.  As a result, the two collided.  Then, the dog, being the omnivore that it is, ate the quick brown fox.  This line is 256 bytes.\r\n"
			"The quick brown fox tried to jump over the yellow dog.  Unfortunately, the yellow dog stood up while the fox was in mid-jump.  As a result, the two collided.  Then, the dog, being the omnivore that it is, ate the quick brown fox.  This line is 252b. \r\n", 1020);

	// Send the packet
	UDPFlush(MySocket);
	
	// Close the socket so it can be used by other modules
	UDPClose(MySocket);
}
コード例 #15
0
ファイル: smtp_demo.c プロジェクト: dakkanner/cst-417-lab
/*****************************************************************************
  Function:
   void SMTPDemo(void)

  Summary:
   Demonstrates use of the e-mail (SMTP) client.

  Description:
   This function demonstrates the use of the SMTP client.  The function is
   called periodically by the stack, and checks if BUTTON2 and BUTTON3 are
   pressed simultaneously.  If they are, it attempts to send an e-mail
   message using parameters hard coded in the function below.

   While the client is executing, LED1 will be used as a busy indicator.
   LED2 will light when the transmission has been completed successfully.
   If both LEDs extinguish, an error occurred.

   For an example of sending a longer message (one that does not exist in
   RAM all at once), see the commented secondary implementation of this
   function in this file (SMTPDemo.c) below.  For an example of sending
   a message using parameters gathered at run time, and/or a message with
   attachments, see the implementation of HTTPPostEmail in CustomHTTPApp.c.

  Precondition:
   The SMTP client is initialized.

  Parameters:
   None

  Returns:
     None
  ***************************************************************************/
void SMTPDemo(void)
{

   // Send an email once if someone pushes BUTTON2 and BUTTON3 at the same time
   // This is a simple message example, where the message
   // body must already be in RAM.
   // LED1 will be used as a busy indicator
   // LED2 will be used as a mail sent successfully indicator
   static enum
   {
       MAIL_HOME = 0,
       MAIL_BEGIN,
       MAIL_SMTP_FINISHING,
       MAIL_DONE
   } MailState = MAIL_HOME;
   static SYS_TICK WaitTime;
   SMTP_POINTERS mySMTPClient;

   switch(MailState)
   {

      case MAIL_HOME:
         if(SYS_USERIO_ButtonGet((SYS_USERIO_BUTTON_1|SYS_USERIO_BUTTON_2),SYS_USERIO_BUTTON_ASSERTED))
         {
            // Start sending an email
            SYS_USERIO_SetLED(SYS_USERIO_LED_1, SYS_USERIO_LED_ASSERTED);
            MailState++;
            SYS_USERIO_SetLED(SYS_USERIO_LED_2, SYS_USERIO_LED_DEASSERTED);
         }
      break;

      case MAIL_BEGIN:
         if(SMTPBeginUsage())
         {
            // Note that these strings must stay allocated in
            // memory until SMTPIsBusy() returns false.  To
            // guarantee that the C compiler does not reuse this
            // memory, you must allocate the strings as static.

            static uint8_t RAMStringTo[] = "*****@*****.**";
            //static uint8_t RAMStringCC[] = "[email protected], \"Jane Smith\" <*****@*****.**>";
            //static uint8_t RAMStringBCC[] = "";
            static uint8_t RAMStringBody[] = "Message generated by stack " TCPIP_STACK_VERSION " \r\n\r\nButtons: 3210";
            RAMStringBody[sizeof(RAMStringBody)-2] = '0' + BUTTON0_IO;
            RAMStringBody[sizeof(RAMStringBody)-3] = '0' + BUTTON1_IO;
            RAMStringBody[sizeof(RAMStringBody)-4] = '0' + BUTTON2_IO;
            RAMStringBody[sizeof(RAMStringBody)-5] = '0' + BUTTON3_IO;

            memset(&mySMTPClient, 0, sizeof(mySMTPClient));
            mySMTPClient.Server = "mail";   // SMTP server address
            //mySMTPClient.Username = "******";
            //mySMTPClient.Password = "******";
            mySMTPClient.To = (char*)RAMStringTo;
            mySMTPClient.From = "\"SMTP Service\" <*****@*****.**>";
            mySMTPClient.Subject = "Hello world!  SMTP Test.";
            mySMTPClient.Body = (char*)RAMStringBody;
            SMTPSendMail(&mySMTPClient);
            MailState++;
         }
         break;

      case MAIL_SMTP_FINISHING:
         if(!SMTPIsBusy())
         {
             // Finished sending mail
             SYS_USERIO_SetLED (SYS_USERIO_LED_1, SYS_USERIO_LED_DEASSERTED);
             MailState++;
             WaitTime = SYS_TICK_Get();
             SYS_USERIO_SetLED(SYS_USERIO_LED_2,(SMTPEndUsage() == SMTP_SUCCESS));
         }
         break;

      case MAIL_DONE:
         // Wait for the user to release BUTTON2 or BUTTON3 and for at
         // least 1 second to pass before allowing another
         // email to be sent.  This is merely to prevent
         // accidental flooding of email boxes while
         // developing code.  Your application may wish to
         // remove this.
         if(SYS_USERIO_ButtonGet((SYS_USERIO_BUTTON_1|SYS_USERIO_BUTTON_2),SYS_USERIO_BUTTON_ASSERTED))
         {
            if(SYS_TICK_Get() - WaitTime > SYS_TICK_TicksPerSecondGet())
               MailState = MAIL_HOME;
         }
         break;
   }
}
コード例 #16
0
/*****************************************************************************
 * FUNCTION: WaitForRawMoveComplete
 *
 * RETURNS: Number of bytes that were overlayed (not always applicable)
 *
 * PARAMS:
 *      rawId   - RAW ID
 *
 *  NOTES: Waits for a RAW move to complete.
 *****************************************************************************/
static uint16_t WaitForRawMoveComplete(uint8_t rawId)

{
    uint8_t  rawIntMask;
    uint16_t byteCount;
    uint8_t  regId;
    bool  intDisabled;
    #if defined(SYS_DEBUG_ENABLE)
    SYS_TICK startTickCount;
    SYS_TICK maxAllowedTicks;
    #endif

    /* create mask to check against for Raw Move complete interrupt for either RAW0 or RAW1 */
    rawIntMask = (rawId == RAW_ID_0)?WF_HOST_INT_MASK_RAW_0_INT_0:WF_HOST_INT_MASK_RAW_1_INT_0;

    /* 
    These variables are shared with the ISR so need to be careful when setting them.
    the WFEintHandler() is the isr that will touch these variables but will only touch
    them if RawMoveState.waitingForRawMoveCompleteInterrupt is set to true.
    RawMoveState.waitingForRawMoveCompleteInterrupt is only set true here and only here.
    so as long as we set RawMoveState.rawInterrupt first and then set RawMoveState.waitingForRawMoveCompleteInterrupt 
    to true, we are guranteed that the ISR won't touch RawMoveState.rawInterrupt and 
    RawMoveState.waitingForRawMoveCompleteInterrupt. 
    */
    RawMoveState.rawInterrupt  = 0;  
    RawMoveState.waitingForRawMoveCompleteInterrupt = true;
    
    // save state of external interrupt here
    intDisabled = WF_EintIsDisabled();
    // if external interrupt is disabled, enable it because we need it for the while(1) loop to exit
    if(intDisabled)
    {
	    WF_EintEnable();
    }
    else if(WF_EintIsPending())
    {
	    WF_EintEnable();
    }

    #if defined(SYS_DEBUG_ENABLE)
    // Before we enter the while loop, get the tick timer count and save it
    maxAllowedTicks = SYS_TICK_TicksPerSecondGet() / 2;  /* 500 ms timeout */
    startTickCount = SYS_TICK_Get();
    #endif
    while (1)
    {
        /* if received an external interrupt that signalled the RAW Move */
        /* completed then break out of this loop                         */
	    if(RawMoveState.rawInterrupt & rawIntMask)
	    {
		    break;
	    }
	    
        #if defined(SYS_DEBUG_ENABLE)
	    /* If timed out waiting for RAW Move complete than lock up */
			#if defined (__C30__)
				uint32_t x = 0;
				T2CON &= 0x7FFF;    // Temporary Workaround for 16 bit device Timer23 read issue
				x = SYS_TICK_Get();
				T2CON |= 0x8000;
	
		        if ((x - startTickCount) >= maxAllowedTicks)
			    {
		    	    SYS_ASSERT(false, "");
			    }
			#else
        		if (SYS_TICK_Get() - startTickCount >= maxAllowedTicks)
	    		{
    	    		SYS_ASSERT(false, "");
	    		}
        	#endif
		#endif
        
    } /* end while */

    /* if interrupt was enabled by us here, we should disable it now that we're finished */
    if(intDisabled)
    {
	    WF_EintDisable();
    }

    /* read the byte count and return it */
    regId = (rawId == RAW_ID_0)?WF_HOST_RAW0_CTRL1_REG:WF_HOST_RAW1_CTRL1_REG;
    byteCount = Read16BitWFRegister(regId); 

    return ( byteCount );
}
コード例 #17
0
ファイル: tcpip_commands.c プロジェクト: ctapang/v0_70_01b
static int _Command_DHCPLeaseInfo(_CMDIO_DEV_NODE* pCmdIO, int argc, char** argv)
{
    TCPIP_NET_HANDLE netH;
    DHCPS_LEASE_HANDLE  prevLease, nextLease;
    DHCPS_LEASE_ENTRY leaseEntry;
    char   addrBuff[20];
const void* cmdIoParam = pCmdIO->cmdIoParam;	

	if (argc != 2)
    {
		(*pCmdIO->pCmdApi->msg)(cmdIoParam, "Usage: dhcpsinfo <interface> \r\n");
		(*pCmdIO->pCmdApi->msg)(cmdIoParam, "Ex: dhcpsinfo PIC32INT \r\n");
		return false;
	}

    netH = TCPIP_STACK_NetHandleGet(argv[1]);
    if (netH == 0)
    {
        (*pCmdIO->pCmdApi->msg)(cmdIoParam, "Unknown interface specified \r\n");
        return false;
    }

	(*pCmdIO->pCmdApi->print)(cmdIoParam,"MAC Address		IPAddress		RemainingLeaseTime \r\n",0);

    prevLease = 0;
    do
    {
        nextLease = TCPIP_DHCPS_LeaseEntryGet(netH, &leaseEntry, prevLease);
		if(!nextLease)
		{
            (*pCmdIO->pCmdApi->print)(cmdIoParam, " \n\r No more entry present \r\n", 0);
		}
        if(nextLease)
        {   // valid info
            // display info
            TCPIP_Helper_MACAddressToString(&leaseEntry.hwAdd, addrBuff, sizeof(addrBuff));
            (*pCmdIO->pCmdApi->msg)(cmdIoParam, addrBuff);
            TCPIP_Helper_IPAddressToString(&leaseEntry.ipAddress, addrBuff, sizeof(addrBuff));
            (*pCmdIO->pCmdApi->print)(cmdIoParam, "	%s ", addrBuff);
            (*pCmdIO->pCmdApi->print)(cmdIoParam, "	%d Secs\r\n", leaseEntry.leaseTime/SYS_TICK_TicksPerSecondGet());

            prevLease = nextLease;
        }
    }while(nextLease != 0);


	return true;

}
コード例 #18
0
/*****************************************************************************
  Function:
	void BerkeleyUDPClientDemo(uint32_t localIP)

  Summary:
	Periodically checks the current time from a pool of servers.

  Description:
	This function periodically checks a pool of time servers to obtain the
	current date/time.

  Precondition:
	UDP is initialized.

  Parameters:
	localIP   - the local interface to use

  Returns:
  	None
  	
  Remarks:
	This function requires once available UDP socket while processing, but
	frees that socket when the SNTP module is idle.
  ***************************************************************************/
void BerkeleyUDPClientDemo(uint32_t localIP)
{
	#if defined(TCPIP_STACK_USE_DNS)
	NTP_PACKET			pkt;
	int			 		i;
	static uint32_t		dwServerIP;
	static SYS_TICK		udpTick;
    static SOCKET		bsdUdpClient;
    int                 udpSkt;
    int 				addrlen = sizeof(struct sockaddr_in);
    static struct sockaddr_in	udpaddr;
    DNS_RESULT  dnsRes;
    
	static enum
	{
		SM_HOME = 0,
		SM_NAME_RESOLVE,
		SM_CREATE_SOCKET,
		SM_BIND,	
		SM_UDP_SEND,
		SM_UDP_RECV,
		SM_SHORT_WAIT,
		SM_WAIT
	} SNTPState = SM_HOME;

	switch(SNTPState)
	{
		case SM_HOME:
			// Obtain ownership of the DNS resolution module
            if(DNSBeginUsage(0) != DNS_RES_OK)
            {
				break;
            }

			// Obtain the IP address associated with the server name
			DNSResolve(NTP_SERVER, DNS_TYPE_A);
			udpTick = SYS_TICK_Get();
			SNTPState = SM_NAME_RESOLVE;
			break;

		case SM_NAME_RESOLVE:
			// Wait for DNS resolution to complete
			dnsRes = DNSIsResolved(NTP_SERVER, (IP_ADDR*)&dwServerIP);
            if(dnsRes == DNS_RES_PENDING)
            {   // still waiting
                break;
            }
            
            // release the DNS module
	    	DNSEndUsage(0);

            if(dnsRes < 0)
            {   // some error
                udpTick = SYS_TICK_Get();
                SNTPState = SM_SHORT_WAIT;
                break;
            }
			
            // DNS_RES_OK
			SNTPState = SM_CREATE_SOCKET;
			// No break needed

		case SM_CREATE_SOCKET:
			udpSkt = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
			if(udpSkt == SOCKET_ERROR)
            {
				return;
            }
            else
            {
                bsdUdpClient = (SOCKET)udpSkt;
            }

// Usually no explicit binding is necessary since we are going to be the first one 
// sending a UDP packet.  sendto() will do implicit binding.  Explicit binding 
// is necessary only when creating UDP servers that will be receiving the first 
// packet.
// However, when using this example with multi-homed hosts we want to use
// a specified network connection specified by the localIP parameter
			SNTPState = SM_BIND;
			// No break needed
			
		case SM_BIND:
            udpaddr.sin_port = 0;
            udpaddr.sin_addr.S_un.S_addr = localIP;
            if( bind(bsdUdpClient, (struct sockaddr*)&udpaddr, addrlen) == SOCKET_ERROR )
                break;

            SNTPState = SM_UDP_SEND;
            // No break needed
            
		case SM_UDP_SEND:
            // Transmit a time request packet
			memset(&pkt, 0, sizeof(pkt));
			pkt.flags.versionNumber = 3;	// NTP Version 3
			pkt.flags.mode = 3;				// NTP Client
			pkt.orig_ts_secs = swapl(NTP_EPOCH);
            udpaddr.sin_port = NTP_SERVER_PORT;
            udpaddr.sin_addr.S_un.S_addr = dwServerIP;
			if(sendto(bsdUdpClient, (const char*)&pkt, sizeof(pkt), 0, (struct sockaddr*)&udpaddr, addrlen)>0)
            {
				udpTick = SYS_TICK_Get();
                SNTPState = SM_UDP_RECV;
            }
			break;

		case SM_UDP_RECV:
			// Look for a response time packet
			i = recvfrom(bsdUdpClient, (char*)&pkt, sizeof(pkt), 0, (struct sockaddr*)&udpaddr, &addrlen);
            if(i < (int)sizeof(pkt))
			{
				if((SYS_TICK_Get()) - udpTick > NTP_REPLY_TIMEOUT * SYS_TICK_TicksPerSecondGet())
				{
					// Abort the request and wait until the next timeout period
					closesocket(bsdUdpClient);
					udpTick = SYS_TICK_Get();
					SNTPState = SM_SHORT_WAIT;
					break;
				}
				break;
			}
			closesocket(bsdUdpClient);
			udpTick = SYS_TICK_Get();
			SNTPState = SM_WAIT;

			// Set out local time to match the returned time
			dwLastUpdateTick = SYS_TICK_Get();
			dwSNTPSeconds = swapl(pkt.tx_ts_secs) - NTP_EPOCH;
			// Do rounding.  If the partial seconds is > 0.5 then add 1 to the seconds count.
			if(((uint8_t*)&pkt.tx_ts_fraq)[0] & 0x80)
				dwSNTPSeconds++;

			break;

		case SM_SHORT_WAIT:
			// Attempt to requery the NTP server after a specified NTP_FAST_QUERY_INTERVAL time (ex: 8 seconds) has elapsed.
			if(SYS_TICK_Get() - udpTick > (NTP_FAST_QUERY_INTERVAL * SYS_TICK_TicksPerSecondGet() ))
				SNTPState = SM_HOME;	
			break;

		case SM_WAIT:
			// Requery the NTP server after a specified NTP_QUERY_INTERVAL time (ex: 10 minutes) has elapsed.
			if(SYS_TICK_Get() - udpTick > (NTP_QUERY_INTERVAL * SYS_TICK_TicksPerSecondGet()))
				SNTPState = SM_HOME;	

			break;
	}

	//#if defined(TCPIP_STACK_USE_DNS)
	#else
		#warning You must define TCPIP_STACK_USE_DNS for BerkeleyUDPClientDemo to work
	#endif
}
コード例 #19
0
/*****************************************************************************
  Function:
    void GenericTCPClient(void)

  Summary:
    Implements a simple HTTP client (over TCP).

  Description:
    This function implements a simple HTTP client, which operates over TCP.
    The function is called periodically by the stack, and waits for BUTTON1
    to be pressed.  When the button is pressed, the application opens a TCP
    connection to an Internet search engine, performs a search for the word
    "Microchip" on "microchip.com", and prints the resulting HTML page to
    the UART.

    This example can be used as a model for many TCP and HTTP client
    applications.

  Precondition:
    TCP is initialized.

  Parameters:
    None

  Returns:
      None
  ***************************************************************************/
void GenericTCPClient(void)
{
    uint8_t                 i;
    uint16_t                w;
    DNS_RESULT          dnsRes;
    uint8_t                vBuffer[9];
    static TCPIP_NET_HANDLE    netH;
    static uint32_t        clientTimer;
    static TCP_SOCKET    MySocket = INVALID_SOCKET;
    static uint32_t nAttempts =0;

    static enum _GenericTCPExampleState
    {
        SM_HOME = 0,
        SM_WAIT_DNS,
        SM_DNS_RESOLVED,
        SM_SOCKET_OBTAINED,
        SM_PROCESS_RESPONSE,
        SM_DISCONNECT,
        SM_DONE
    } GenericTCPExampleState = SM_DONE;

    //DBPRINTF("    Starting TCP client\n");

    switch(GenericTCPExampleState)
    {

        case SM_HOME:

            DBPRINTF("  SM_HOME\n");
            netH = TCPIP_STACK_GetDefaultNet();
            if(DNSBeginUsage(netH) != DNS_RES_OK)
            {
                break;
            }
            DNSResolve(ServerName, DNS_TYPE_A); 
            GenericTCPExampleState++;
            break;

        case SM_WAIT_DNS:

            DBPRINTF("  SM_WAIT_DNS\n");
            dnsRes = DNSIsResolved(ServerName, &serverIP);
            if(dnsRes == DNS_RES_PENDING)
            {   // ongoing operation;
                break;
            }
            else if(dnsRes < 0)
            {   // some DNS error occurred; retry
                DBPRINTF((const char*)"\r\n\r\nGeneric TCP client: DNS name resolving failed...\r\n");
                TCPClose(MySocket);
                MySocket = INVALID_SOCKET;
                GenericTCPExampleState = SM_HOME;
                nAttempts++;
                if(nAttempts>8) // After 8 attempts give-up
                {
                    GenericTCPExampleState = SM_DONE;
                    nAttempts=0;
                }
            }
            else
            {
                clientTimer = SYS_TICK_Get();
                GenericTCPExampleState++;
            }
            DNSEndUsage(netH);
            break;

        case SM_DNS_RESOLVED:
            DBPRINTF("  SM_DNS_RESOLVED\n");
            // Connect the socket to the remote TCP server
            MySocket = TCPOpenClient(IP_ADDRESS_TYPE_IPV4, ServerPort, (IP_MULTI_ADDRESS*)&serverIP);

			// Abort operation if no TCP socket could be opened.
			// If this ever happens, you need to update your tcp_config.h
            if(MySocket == INVALID_SOCKET)
            {   // retry
                break;
            }

            GenericTCPExampleState++;
            clientTimer = SYS_TICK_Get();
            break;

        case SM_SOCKET_OBTAINED:

            DBPRINTF("  SM_SOCKET_OBTAINED\n");
            // Wait for the remote server to accept our connection request
            if(!TCPIsConnected(MySocket))
            {
                // Time out if more than 5 seconds is spent in this state
                if((SYS_TICK_Get()-clientTimer) > 5 * SYS_TICK_TicksPerSecondGet() )
                {
                    // Close the socket so it can be used by other modules
                    TCPClose(MySocket);
                    MySocket = INVALID_SOCKET;
                    GenericTCPExampleState--;
                    DBPRINTF((const char*)"\r\n\r\nGeneric TCP client: Failed connecting to the remote server...\r\n");
                }
                break;
            }

            clientTimer = SYS_TICK_Get();

            // Make certain the socket can be written to
            if(TCPIsPutReady(MySocket) < 125u)
                break;

            // Place the application protocol data into the transmit buffer.  For this example, we are connected to an HTTP server, so we'll send an HTTP GET request.
            TCPPutString(MySocket, (const uint8_t*)"GET ");
            TCPPutString(MySocket, RemoteURL);
            TCPPutString(MySocket, (const uint8_t*)" HTTP/1.0\r\nHost: ");
            TCPPutString(MySocket, (const uint8_t*)ServerName);
            TCPPutString(MySocket, (const uint8_t*)"\r\nConnection: close\r\n\r\n");

            // Send the packet
            TCPFlush(MySocket);
            GenericTCPExampleState++;
            break;

        case SM_PROCESS_RESPONSE:
            //DBPRINTF("  SM_PROCESS_RESPONSE\n");
            // Check to see if the remote node has disconnected from us or sent us any application data
            // If application data is available, write it to the UART
            if(!TCPIsConnected(MySocket))
            {
                GenericTCPExampleState = SM_DISCONNECT;
                // Do not break;  We might still have data in the TCP RX FIFO waiting for us
            }

            // Get count of RX bytes waiting
            w = TCPIsGetReady(MySocket);

            // Obtian and print the server reply
            i = sizeof(vBuffer)-1;
            vBuffer[i] = '\0';
            while(w)
            {
                if(w < i)
                {
                    i = w;
                    vBuffer[i] = '\0';
                }
                w -= TCPGetArray(MySocket, vBuffer, i);
#if defined(GENERIC_TCP_CLIENT_ENABLE_UART_DUMP)
                DBPRINTF((char*)vBuffer);
#endif
                // SYS_CONSOLE_MESSAGE is a blocking call which will slow down the rest of the stack
                // if we shovel the whole TCP RX FIFO into the serial port all at once.
                // Therefore, let's break out after only one chunk most of the time.  The
                // only exception is when the remote node disconncets from us and we need to
                // use up all the data before changing states.
                if(GenericTCPExampleState == SM_PROCESS_RESPONSE)
                    break;
            }

            break;

        case SM_DISCONNECT:
            DBPRINTF("  SM_DISCONNECT\n");
            // Close the socket so it can be used by other modules
            // For this application, we wish to stay connected, but this state will still get entered if the remote server decides to disconnect
            TCPClose(MySocket);
            MySocket = INVALID_SOCKET;
            GenericTCPExampleState = SM_DONE;
            break;

        case SM_DONE:
            //DBPRINTF("  SM_DONE\n");
            // Do nothing unless the user pushes BUTTON1 and wants to restart the whole connection/download process
            // On many boards, SYS_USERIO_BUTTON_0 is assigned to sw1
            // SYS_USERIO_BUTTON_1=sw2 and SYS_USERIO_BUTTON_2=sw3
            if(SYS_USERIO_ButtonGet((SYS_USERIO_BUTTON_1),SYS_USERIO_BUTTON_ASSERTED))
                GenericTCPExampleState = SM_HOME;
            break;
    }
}
コード例 #20
0
/*****************************************************************************
  Function:
    void GenericSSLClient(void)

  Summary:
    Implements a simple HTTP client (over TCP).

  Description:
    This function implements a simple HTTP client, which operates over TCP.  
    The function is called periodically by the stack, and waits for BUTTON1 
    to be pressed.  When the button is pressed, the application opens a TCP
    connection to an Internet search engine, performs a search for the word
    "Microchip" on "microchip.com", and prints the resulting HTML page to
    the UART.  
    
    To add this to an existing application, make the call to GenericSSLClient 
    from StackTasks.
    
    This example can be used as a model for many TCP and HTTP client
    applications.

  Precondition:
    TCP is initialized.

  Parameters:
    None

  Returns:
    None
  ***************************************************************************/
void GenericSSLClient(void)
{
    uint8_t             i;
    uint16_t            w;
    DNS_RESULT          dnsRes;
    uint8_t             vBuffer[9];
    static TCPIP_NET_HANDLE    netH;
    static uint32_t     clientTimer;
    static TCP_SOCKET   MySocket = INVALID_SOCKET;
    static enum _GenericTCPExampleState
    {
        SM_HOME = 0,
        SM_WAIT_DNS,
        SM_DNS_RESOLVED,
        SM_SOCKET_OBTAINED,
        SM_START_SSL,
        SM_PROCESS_RESPONSE,
        SM_DISCONNECT,
        SM_DONE
    } GenericTCPExampleState = SM_DONE;

    switch(GenericTCPExampleState)
    {

        case SM_HOME:
            
            netH = TCPIP_STACK_GetDefaultNet();
            dnsRes = DNSBeginUsage(netH);
            if(dnsRes != DNS_RES_OK)
                break;
            DNSResolve(SSLServerName, DNS_TYPE_A);
            GenericTCPExampleState++;
            break;

        case SM_WAIT_DNS:
            
            dnsRes = DNSIsResolved(SSLServerName, &serverIP_SSL);
            if(dnsRes == DNS_RES_PENDING)
            {   // ongoing operation;
                break;
            }
            else if(dnsRes < 0)
            {   // some DNS error occurred; retry
                SYS_CONSOLE_MESSAGE((const char*)"\r\n\r\nDNS name resolving failed...\r\n");
                TCPClose(MySocket);
                MySocket = INVALID_SOCKET;
                GenericTCPExampleState = SM_HOME;
            }
            else
            {
                clientTimer = SYS_TICK_Get();
                GenericTCPExampleState++;
            }
            DNSEndUsage(netH);
            break;

        case SM_DNS_RESOLVED:
            // Connect the socket to the remote TCP server
            MySocket = TCPOpenClient(IP_ADDRESS_TYPE_IPV4, SSLServerPort, (IP_MULTI_ADDRESS*)&serverIP_SSL);
            
			// Abort operation if no TCP socket could be opened.
			// If this ever happens, you need to update your tcp_config.h
            if(MySocket == INVALID_SOCKET)
            {   // retry
                break;
            }

            SYS_CONSOLE_MESSAGE((const char*)"\r\n\r\nConnecting using Microchip TCP API...\r\n");

            GenericTCPExampleState++;
            clientTimer = SYS_TICK_Get();
            break;

        case SM_SOCKET_OBTAINED:

            // Wait for the remote server to accept our connection request
            if(!TCPIsConnected(MySocket))
            {
                // Time out if more than 5 seconds is spent in this state
                if((SYS_TICK_Get()-clientTimer) > 5 * SYS_TICK_TicksPerSecondGet() )
                {
                    // Close the socket so it can be used by other modules
                    TCPClose(MySocket);
                    MySocket = INVALID_SOCKET;
                    GenericTCPExampleState--;
                    SYS_CONSOLE_MESSAGE((const char*)"\r\n\r\nFailed connecting to the remote server...\r\n");
                }
                break;
            }

            clientTimer = SYS_TICK_Get();

            if(!TCPStartSSLClient(MySocket,(uint8_t *)"thishost"))
                break;

            GenericTCPExampleState++;
            break;

        case SM_START_SSL:
            if (TCPSSLIsHandshaking(MySocket)) 
            {
                // Handshaking may fail if the SSL_RSA_CLIENT_SIZE is not large enough
                // for the server’s certificate
                if(SYS_TICK_Get()-clientTimer > 10*SYS_TICK_TicksPerSecondGet())
                {
                    // Close the socket so it can be used by other modules
                    TCPClose(MySocket);
                    MySocket = INVALID_SOCKET;
                    GenericTCPExampleState=SM_HOME;
                }
                break;
            }


            // Make certain the socket can be written to
            if(TCPIsPutReady(MySocket) < 125u)
                break;
            
            // Place the application protocol data into the transmit buffer.  For this example, we are connected to an HTTP server, so we'll send an HTTP GET request.
            TCPPutString(MySocket, (const uint8_t*)"GET ");
            TCPPutString(MySocket, SSLRemoteURL);
            TCPPutString(MySocket, (const uint8_t*)" HTTP/1.0\r\nHost: ");
            TCPPutString(MySocket, (const uint8_t*)SSLServerName);
            TCPPutString(MySocket, (const uint8_t*)"\r\nConnection: close\r\n\r\n");

            // Send the packet
            TCPFlush(MySocket);
            GenericTCPExampleState++;
            break;

        case SM_PROCESS_RESPONSE:
            // Check to see if the remote node has disconnected from us or sent us any application data
            // If application data is available, write it to the UART
            if(!TCPIsConnected(MySocket))
            {
                GenericTCPExampleState = SM_DISCONNECT;
                // Do not break;  We might still have data in the TCP RX FIFO waiting for us
            }
    
            // Get count of RX bytes waiting
            w = TCPIsGetReady(MySocket);    
    
            // Obtian and print the server reply
            i = sizeof(vBuffer)-1;
            vBuffer[i] = '\0';
            while(w)
            {
                if(w < i)
                {
                    i = w;
                    vBuffer[i] = '\0';
                }
                w -= TCPGetArray(MySocket, vBuffer, i);
                SYS_CONSOLE_MESSAGE((char*)vBuffer);
                
                // SYS_CONSOLE_MESSAGE is a blocking call which will slow down the rest of the stack 
                // if we shovel the whole TCP RX FIFO into the serial port all at once.  
                // Therefore, let's break out after only one chunk most of the time.  The 
                // only exception is when the remote node disconncets from us and we need to 
                // use up all the data before changing states.
                if(GenericTCPExampleState == SM_PROCESS_RESPONSE)
                    break;
            }
    
            break;
    
        case SM_DISCONNECT:
            // Close the socket so it can be used by other modules
            // For this application, we wish to stay connected, but this state will still get entered if the remote server decides to disconnect
            TCPClose(MySocket);
            MySocket = INVALID_SOCKET;
            GenericTCPExampleState = SM_DONE;
            break;
    
        case SM_DONE:
            // Do nothing unless the user pushes BUTTON1 and wants to restart the whole connection/download process
            if(BUTTON1_IO == 0u)
                GenericTCPExampleState = SM_HOME;
            break;
    }
}
コード例 #21
0
ファイル: main_demo.c プロジェクト: ctapang/v0_70_01b
//
// Main application entry point.
//
int main(void)
{
    static SYS_TICK startTick = 0;
    static IPV4_ADDR dwLastIP[2] = { {-1}, {-1} };
    IPV4_ADDR           ipAddr;

    SYS_USERIO_LED_STATE LEDstate = SYS_USERIO_LED_DEASSERTED;
    int                 i, nNets;
    TCPIP_NET_HANDLE    netH;
    const char          *netName, *netBiosName;

#if defined (TCPIP_STACK_USE_ZEROCONF_MDNS_SD)
    char mDNSServiceName[] = "MyWebServiceNameX ";     // base name of the service Must not exceed 16 bytes long
                                                       // the last digit will be incremented by interface
#endif  // defined (TCPIP_STACK_USE_ZEROCONF_MDNS_SD)


    // perform system initialization
    SYS_Initialize(0);

    SYS_CONSOLE_MESSAGE("\r\n\n\n ---  TCPIP Demo Starts!  --- \r\n");
    SYS_OUT_MESSAGE("TCPIPStack " TCPIP_STACK_VERSION "  ""                ");

        // Display the names associated with each interface
    nNets = TCPIP_STACK_NumberOfNetworksGet();
    for(i = 0; i < nNets; i++)
    {

        netH = TCPIP_STACK_IndexToNet(i);
        netName = TCPIP_STACK_NetNameGet(netH);
        netBiosName = TCPIP_STACK_NetBIOSName(netH);

#if defined(TCPIP_STACK_USE_NBNS)
        SYS_CONSOLE_PRINT("    Interface %s on host %s - NBNS enabled\r\n", netName, netBiosName);
#else
        SYS_CONSOLE_PRINT("    Interface %s on host %s - NBNS disabled\r\n", netName, netBiosName);
#endif  // defined(TCPIP_STACK_USE_NBNS)

#if defined (TCPIP_STACK_USE_ZEROCONF_MDNS_SD)
        mDNSServiceName[sizeof(mDNSServiceName) - 2] = '1' + i;
        TCPIP_MDNS_ServiceRegister( netH
                , mDNSServiceName                   // name of the service
                ,"_http._tcp.local"                 // type of the service
                ,80                                 // TCP or UDP port, at which this service is available
                ,((const uint8_t *)"path=/index.htm")  // TXT info
                ,1                                  // auto rename the service when if needed
                ,NULL                               // no callback function
                ,NULL);                             // no application context
#endif //TCPIP_STACK_USE_ZEROCONF_MDNS_SD
    }

#if defined(WF_UPDATE_FIRMWARE_UART_24G)
    extern bool    WF_FirmwareUpdate_Uart_24G(void);
    WF_FirmwareUpdate_Uart_24G();
#endif

    // Now that all items are initialized, begin the co-operative
    // multitasking loop.  This infinite loop will continuously
    // execute all stack-related tasks, as well as your own
    // application's functions.  Custom functions should be added
    // at the end of this loop.
    // Note that this is a "co-operative mult-tasking" mechanism
    // where every task performs its tasks (whether all in one shot
    // or part of it) and returns so that other tasks can do their
    // job.
    // If a task needs very long time to do its job, it must be broken
    // down into smaller pieces so that other tasks can have CPU time.
    while (1)
    {
        SYS_Tasks();

        // Blink LED0 every second.
        if (SYS_TICK_Get() - startTick >= SYS_TICK_TicksPerSecondGet() / 2ul)
        {
            startTick = SYS_TICK_Get();
            LEDstate ^= SYS_USERIO_LED_ASSERTED;
            SYS_USERIO_SetLED(SYS_USERIO_LED_0, LEDstate);
        }

        // if the IP address of an interface has changed
        // display the new value on the system console
        nNets = TCPIP_STACK_NumberOfNetworksGet();
        for (i = 0; i < nNets; i++)
        {
            netH = TCPIP_STACK_IndexToNet(i);
            ipAddr.Val = TCPIP_STACK_NetAddress(netH);
            if(dwLastIP[i].Val != ipAddr.Val)
            {
                dwLastIP[i].Val = ipAddr.Val;

                SYS_CONSOLE_MESSAGE(TCPIP_STACK_NetNameGet(netH));
                SYS_CONSOLE_MESSAGE(" IP Address: ");
                SYS_CONSOLE_PRINT("%d.%d.%d.%d \r\n", ipAddr.v[0], ipAddr.v[1], ipAddr.v[2], ipAddr.v[3]);
            }
        }

#if (WF_DEFAULT_NETWORK_TYPE == WF_NETWORK_TYPE_SOFT_AP)

        if (g_scan_done) {
           if (g_prescan_waiting) {
               SYS_CONSOLE_MESSAGE((const char*)"\n SoftAP prescan results ........ \r\n\n");
               SCANCXT.displayIdx = 0;
               extern void WFDisplayScanMgr(void);
               while (IS_SCAN_STATE_DISPLAY(SCANCXT.scanState)) {
                   WFDisplayScanMgr();
               }
               SYS_CONSOLE_MESSAGE((const char*)"\r\n ");

       #if defined(WF_CS_TRIS)
                Demo_Wifi_Connect();
       #endif
               g_scan_done = 0;
               g_prescan_waiting = 0;
           }
        }
#endif // (WF_DEFAULT_NETWORK_TYPE == WF_NETWORK_TYPE_SOFT_AP)

#if defined(WF_UPDATE_FIRMWARE_UART_24G)
    WF_FirmwareUpdate_Uart_24G();
#endif

#if defined(WF_UPDATE_FIRMWARE_TCPCLIENT_24G)
    WF_FirmwareUpdate_TcpClient_24G();
#endif

    }
}
コード例 #22
0
ファイル: smtp.c プロジェクト: dakkanner/cst-417-lab
/*****************************************************************************
  Function:
	void SMTPClientTask(void)

  Summary:
	Performs any pending SMTP client tasks

  Description:
	This function handles periodic tasks associated with the SMTP client,
	such as processing initial connections and command sequences.

  Precondition:
	None

  Parameters:
	None

  Returns:
	None

  Remarks:
	This function acts as a task (similar to one in an RTOS).  It
	performs its task in a co-operative manner, and the main application
	must call this function repeatedly to ensure that all open or new
	connections are served in a timely fashion.
  ***************************************************************************/
void SMTPClientTask(void)
{
    uint8_t			i;
    uint16_t			w;
    uint8_t			vBase64Buffer[4];
    static SYS_TICK	SMTPTimer;
    static uint8_t		RXBuffer[4];
    static const uint8_t *ROMStrPtr, *ROMStrPtr2;
    static const uint8_t *RAMStrPtr;
    static uint16_t		wAddressLength;
    DNS_RESULT      dnsRes;

    switch(TransportState)
    {
    case TRANSPORT_HOME:
        // SMTPBeginUsage() is the only function which will kick
        // the state machine into the next state
        break;

    case TRANSPORT_BEGIN:
        // Wait for the user to program all the pointers and then
        // call SMTPSendMail()
        if(!SMTPFlags.bits.ReadyToStart)
            break;

        // Obtain ownership of the DNS resolution module
        if(DNSBeginUsage(0) != DNS_RES_OK)
        {
            break;
        }

        // Obtain the IP address associated with the SMTP mail server
        if(SMTPClient.Server)
        {
            DNSResolve((const char*)SMTPClient.Server, DNS_TYPE_A);
        }
        else
        {
            // If we don't have a mail server, try to send the mail
            // directly to the destination SMTP server
            if(SMTPClient.To)
            {
                SMTPClient.Server = strchr((char*)SMTPClient.To, '@');
            }

            if(!(SMTPClient.Server))
            {
                if(SMTPClient.CC)
                {
                    SMTPClient.Server = strchr((char*)SMTPClient.CC, '@');
                }
            }

            if(!(SMTPClient.Server))
            {
                if(SMTPClient.BCC)
                {
                    SMTPClient.Server = strchr((char*)SMTPClient.BCC, '@');
                }
            }

            // See if we found a hostname anywhere which we could resolve
            if(!(SMTPClient.Server))
            {
                DNSEndUsage(0);
                ResponseCode = SMTP_RESOLVE_ERROR;
                TransportState = TRANSPORT_HOME;
                break;
            }

            // Skip over the @ sign and resolve the host name
            SMTPClient.Server++;
            DNSResolve((const char*)SMTPClient.Server, DNS_TYPE_MX);
        }

        SMTPTimer = SYS_TICK_Get();
        TransportState++;
        break;

    case TRANSPORT_NAME_RESOLVE:
        // Wait for the DNS server to return the requested IP address
        dnsRes = DNSIsResolved((const char*)SMTPClient.Server, &SMTPServer);

        if(dnsRes == DNS_RES_PENDING)
        {
            break;
        }

        // Release the DNS module
        DNSEndUsage(0);

        if(dnsRes < 0)
        {   // some error occurred
            ResponseCode = SMTP_RESOLVE_ERROR;
            TransportState = TRANSPORT_HOME;
            break;
        }

        // DNS_RES_OK
        TransportState++;
    // No need to break here

    case TRANSPORT_OBTAIN_SOCKET:
        // Connect a TCP socket to the remote SMTP server
        MySocket = TCPOpenClient(IP_ADDRESS_TYPE_IPV4, SMTPClient.ServerPort, (IP_MULTI_ADDRESS*)&SMTPServer.Val);

        // Abort operation if no TCP socket could be opened.
        // If this ever happens, you need to update your tcp_config.h
        if(MySocket == INVALID_SOCKET)
            break;

        TransportState++;
        SMTPTimer = SYS_TICK_Get();
        // No break; fall into TRANSPORT_SOCKET_OBTAINED

#if defined(TCPIP_STACK_USE_SSL_CLIENT)
    case TRANSPORT_SECURING_SOCKET:
        if(!TCPIsConnected(MySocket))
        {
            // Don't stick around in the wrong state if the
            // server was connected, but then disconnected us.
            // Also time out if we can't establish the connection
            // to the SMTP server
            if((SYS_TICK_Get()-SMTPTimer) > (SMTP_SERVER_REPLY_TIMEOUT * SYS_TICK_TicksPerSecondGet()))
            {
                ResponseCode = SMTP_CONNECT_ERROR;
                TransportState = TRANSPORT_CLOSE;
            }

            break;
        }
        SMTPFlags.bits.ConnectedOnce = true;

        // Start SSL if needed for this connection
        if(SMTPClient.UseSSL && !TCPStartSSLClient(MySocket,NULL))
            break;

        // Move on to main state
        SMTPTimer = SYS_TICK_Get();
        TransportState++;
        break;
#endif

    case TRANSPORT_SOCKET_OBTAINED:
        if(!TCPIsConnected(MySocket))
        {
            // Don't stick around in the wrong state if the
            // server was connected, but then disconnected us.
            // Also time out if we can't establish the connection
            // to the SMTP server
            if(SMTPFlags.bits.ConnectedOnce || ((SYS_TICK_Get()-SMTPTimer) > (SMTP_SERVER_REPLY_TIMEOUT * SYS_TICK_TicksPerSecondGet())))
            {
                ResponseCode = SMTP_CONNECT_ERROR;
                TransportState = TRANSPORT_CLOSE;
            }

            break;
        }
        SMTPFlags.bits.ConnectedOnce = true;

#if defined(TCPIP_STACK_USE_SSL_CLIENT)
        // Make sure the SSL handshake has completed
        if(SMTPClient.UseSSL && TCPSSLIsHandshaking(MySocket))
            break;
#endif

        // See if the server sent us anything
        while(TCPIsGetReady(MySocket))
        {
            TCPGet(MySocket, &i);
            switch(RXParserState)
            {
            case RX_BYTE_0:
            case RX_BYTE_1:
            case RX_BYTE_2:
                RXBuffer[RXParserState] = i;
                RXParserState++;
                break;

            case RX_BYTE_3:
                switch(i)
                {
                case ' ':
                    SMTPFlags.bits.RXSkipResponse = false;
                    RXParserState++;
                    break;
                case '-':
                    SMTPFlags.bits.RXSkipResponse = true;
                    RXParserState++;
                    break;
                case '\r':
                    RXParserState = RX_SEEK_LF;
                    break;
                }
                break;

            case RX_SEEK_CR:
                if(i == '\r')
                    RXParserState++;
                break;

            case RX_SEEK_LF:
                // If we received the whole command
                if(i == '\n')
                {
                    RXParserState = RX_BYTE_0;

                    if(!SMTPFlags.bits.RXSkipResponse)
                    {
                        // The server sent us a response code
                        // Null terminate the ASCII reponse code so we can convert it to an integer
                        RXBuffer[3] = 0;
                        ResponseCode = atoi((char*)RXBuffer);

                        // Handle the response
                        switch(SMTPState)
                        {
                        case SMTP_HELO_ACK:
                            if(ResponseCode >= 200u && ResponseCode <= 299u)
                            {
                                if(SMTPClient.Username)
                                    SMTPState = SMTP_AUTH_LOGIN;
                                else
                                    SMTPState = SMTP_MAILFROM;
                            }
                            else
                                SMTPState = SMTP_QUIT_INIT;
                            break;


                        case SMTP_AUTH_LOGIN_ACK:
                        case SMTP_AUTH_USERNAME_ACK:
                            if(ResponseCode == 334u)
                                SMTPState++;
                            else
                                SMTPState = SMTP_QUIT_INIT;
                            break;

                        case SMTP_AUTH_PASSWORD_ACK:
                            if(ResponseCode == 235u)
                                SMTPState++;
                            else
                                SMTPState = SMTP_QUIT_INIT;
                            break;

                        case SMTP_HOME:
                        case SMTP_MAILFROM_ACK:
                        case SMTP_RCPTTO_ACK:
                        case SMTP_RCPTTOCC_ACK:
                        case SMTP_RCPTTOBCC_ACK:
                            if(ResponseCode >= 200u && ResponseCode <= 299u)
                                SMTPState++;
                            else
                                SMTPState = SMTP_QUIT_INIT;
                            break;

                        case SMTP_DATA_ACK:
                            if(ResponseCode == 354u)
                                SMTPState++;
                            else
                                SMTPState = SMTP_QUIT_INIT;
                            break;

                        case SMTP_DATA_BODY_ACK:
                            if(ResponseCode >= 200u && ResponseCode <= 299u)
                                SMTPFlags.bits.SentSuccessfully = true;

                            SMTPState = SMTP_QUIT_INIT;
                            break;

                        // Default case needed to supress compiler diagnostics
                        default:
                            break;
                        }
                    }
                }
                else if(i != '\r')
                    RXParserState--;

                break;
            }
        }

        // Generate new data in the TX buffer, as needed, if possible
        if(TCPIsPutReady(MySocket) < 64u)
            break;

        switch(SMTPState)
        {
        case SMTP_HELO:
            if(SMTPClient.Username == NULL)
                TCPPutString(MySocket, (uint8_t*)"HELO MCHPBOARD\r\n");
            else
                TCPPutString(MySocket, (uint8_t*)"EHLO MCHPBOARD\r\n");
            TCPFlush(MySocket);
            SMTPState++;
            break;

        case SMTP_AUTH_LOGIN:
            // Note: This state is only entered from SMTP_HELO_ACK if the application
            // has specified a Username to use (SMTPClient.Username is non-NULL)
            TCPPutString(MySocket, (uint8_t*)"AUTH LOGIN\r\n");
            TCPFlush(MySocket);
            SMTPState++;
            break;

        case SMTP_AUTH_USERNAME:
            // Base 64 encode and transmit the username.
            RAMStrPtr = (uint8_t*)SMTPClient.Username;
            w = strlen((char*)RAMStrPtr);

            while(w)
            {
                i = 0;
                while((i < w) && (i < sizeof(vBase64Buffer)*3/4))
                {
                    vBase64Buffer[i] = *RAMStrPtr++;
                    i++;
                }
                w -= i;
                TCPIP_Helper_Base64Encode(vBase64Buffer, i, vBase64Buffer, sizeof(vBase64Buffer));
                TCPPutArray(MySocket, vBase64Buffer, sizeof(vBase64Buffer));
            }
            TCPPutString(MySocket, (uint8_t*)"\r\n");
            TCPFlush(MySocket);
            SMTPState++;
            break;

        case SMTP_AUTH_PASSWORD:
            // Base 64 encode and transmit the password
            RAMStrPtr = (uint8_t*)SMTPClient.Password;
            w = strlen((char*)RAMStrPtr);

            while(w)
            {
                i = 0;
                while((i < w) && (i < sizeof(vBase64Buffer)*3/4))
                {
                    vBase64Buffer[i] = *RAMStrPtr++;
                    i++;
                }
                w -= i;
                TCPIP_Helper_Base64Encode(vBase64Buffer, i, vBase64Buffer, sizeof(vBase64Buffer));
                TCPPutArray(MySocket, vBase64Buffer, sizeof(vBase64Buffer));
            }
            TCPPutString(MySocket, (uint8_t*)"\r\n");
            TCPFlush(MySocket);
            SMTPState++;
            break;

        case SMTP_MAILFROM:
            // Send MAIL FROM header.  Note that this is for the SMTP server validation,
            // not what actually will be displayed in the recipients mail client as a
            // return address.
            TCPPutString(MySocket, (uint8_t*)"MAIL FROM:<");
            RAMStrPtr = FindEmailAddress((uint8_t*)SMTPClient.From, &wAddressLength);
            TCPPutArray(MySocket, RAMStrPtr, wAddressLength);
            TCPPutString(MySocket, (uint8_t*)">\r\n");
            TCPFlush(MySocket);
            SMTPState++;
            break;

        case SMTP_RCPTTO_INIT:
            // See if there are any (To) recipients to process
            if(SMTPClient.To)
            {
                RAMStrPtr = FindEmailAddress((uint8_t*)SMTPClient.To, &wAddressLength);
                if(wAddressLength)
                {
                    SMTPState = SMTP_RCPTTO;
                    break;
                }
            }

            SMTPState = SMTP_RCPTTOCC_INIT;
            break;

        case SMTP_RCPTTO:
        case SMTP_RCPTTOCC:
        case SMTP_RCPTTOBCC:
            TCPPutString(MySocket, (uint8_t*)"RCPT TO:<");
            TCPPutArray(MySocket, RAMStrPtr, wAddressLength);
            TCPPutString(MySocket, (uint8_t*)">\r\n");
            TCPFlush(MySocket);
            SMTPState++;
            break;

        case SMTP_RCPTTO_ISDONE:
            // See if we have any more (To) recipients to process
            // If we do, we must roll back a couple of states
            RAMStrPtr = FindEmailAddress(RAMStrPtr+wAddressLength, &wAddressLength);

            if(wAddressLength)
            {
                SMTPState = SMTP_RCPTTO;
                break;
            }

            // All done with To field
            SMTPState++;
        //No break

        case SMTP_RCPTTOCC_INIT:
            // See if there are any Carbon Copy (CC) recipients to process
            if(SMTPClient.CC)
            {
                RAMStrPtr = FindEmailAddress((uint8_t*)SMTPClient.CC, &wAddressLength);
                if(wAddressLength)
                {
                    SMTPState = SMTP_RCPTTOCC;
                    break;
                }
            }

            SMTPState = SMTP_RCPTTOBCC_INIT;
            break;

        case SMTP_RCPTTOCC_ISDONE:
            // See if we have any more Carbon Copy (CC) recipients to process
            // If we do, we must roll back a couple of states
            RAMStrPtr = FindEmailAddress(RAMStrPtr+wAddressLength, &wAddressLength);

            if(wAddressLength)
            {
                SMTPState = SMTP_RCPTTOCC;
                break;
            }

            // All done with CC field
            SMTPState++;
        //No break

        case SMTP_RCPTTOBCC_INIT:
            // See if there are any Blind Carbon Copy (BCC) recipients to process
            if(SMTPClient.BCC)
            {
                RAMStrPtr = FindEmailAddress((uint8_t*)SMTPClient.BCC, &wAddressLength);
                if(wAddressLength)
                {
                    SMTPState = SMTP_RCPTTOBCC;
                    break;
                }
            }

            // All done with BCC field
            SMTPState = SMTP_DATA;
            break;

        case SMTP_RCPTTOBCC_ISDONE:
            // See if we have any more Blind Carbon Copy (CC) recipients to process
            // If we do, we must roll back a couple of states
            RAMStrPtr = FindEmailAddress(RAMStrPtr+wAddressLength, &wAddressLength);

            if(wAddressLength)
            {
                SMTPState = SMTP_RCPTTOBCC;
                break;
            }

            // All done with BCC field
            SMTPState++;
        //No break

        case SMTP_DATA:
            TCPPutString(MySocket, (uint8_t*)"DATA\r\n");
            SMTPState++;
            PutHeadersState = PUTHEADERS_FROM_INIT;
            TCPFlush(MySocket);
            break;

        case SMTP_DATA_HEADER:
            while((PutHeadersState != PUTHEADERS_DONE) && (TCPIsPutReady(MySocket) > 64u))
            {
                switch(PutHeadersState)
                {
                case PUTHEADERS_FROM_INIT:
                    if(SMTPClient.From)
                    {
                        PutHeadersState = PUTHEADERS_FROM;
                        TCPPutString(MySocket, (uint8_t*)"From: ");
                    }
                    else
                    {
                        PutHeadersState = PUTHEADERS_TO_INIT;
                    }
                    break;

                case PUTHEADERS_FROM:
                    SMTPClient.From = (char*)TCPPutString(MySocket, (uint8_t*)SMTPClient.From);
                    if(*SMTPClient.From == 0u)
                        PutHeadersState = PUTHEADERS_TO_INIT;
                    break;

                case PUTHEADERS_TO_INIT:
                    if(SMTPClient.To)
                    {
                        PutHeadersState = PUTHEADERS_TO;
                        TCPPutString(MySocket, (uint8_t*)"\r\nTo: ");
                    }
                    else
                    {
                        PutHeadersState = PUTHEADERS_CC_INIT;
                    }
                    break;

                case PUTHEADERS_TO:
                    SMTPClient.To = (char*)TCPPutString(MySocket, (uint8_t*)SMTPClient.To);
                    if(*SMTPClient.To == 0u)
                        PutHeadersState = PUTHEADERS_CC_INIT;
                    break;

                case PUTHEADERS_CC_INIT:
                    if(SMTPClient.CC)
                    {
                        PutHeadersState = PUTHEADERS_CC;
                        TCPPutString(MySocket, (uint8_t*)"\r\nCC: ");
                    }
                    else
                    {
                        PutHeadersState = PUTHEADERS_SUBJECT_INIT;
                    }
                    break;

                case PUTHEADERS_CC:
                    SMTPClient.CC = (char*)TCPPutString(MySocket, (uint8_t*)SMTPClient.CC);
                    if(*SMTPClient.CC == 0u)
                        PutHeadersState = PUTHEADERS_SUBJECT_INIT;
                    break;

                case PUTHEADERS_SUBJECT_INIT:
                    if(SMTPClient.Subject)
                    {
                        PutHeadersState = PUTHEADERS_SUBJECT;
                        TCPPutString(MySocket, (uint8_t*)"\r\nSubject: ");
                    }
                    else
                    {
                        PutHeadersState = PUTHEADERS_OTHER_INIT;
                    }
                    break;

                case PUTHEADERS_SUBJECT:
                    SMTPClient.Subject = (char*)TCPPutString(MySocket, (uint8_t*)SMTPClient.Subject);
                    if(*SMTPClient.Subject == 0u)
                        PutHeadersState = PUTHEADERS_OTHER_INIT;
                    break;

                case PUTHEADERS_OTHER_INIT:
                    TCPPutArray(MySocket, (uint8_t*)"\r\n", 2);
                    if(SMTPClient.OtherHeaders)
                    {
                        PutHeadersState = PUTHEADERS_OTHER;
                    }
                    else
                    {
                        TCPPutArray(MySocket, (uint8_t*)"\r\n", 2);
                        PutHeadersState = PUTHEADERS_DONE;
                        SMTPState++;
                    }
                    break;

                case PUTHEADERS_OTHER:
                    SMTPClient.OtherHeaders = (char*)TCPPutString(MySocket, (uint8_t*)SMTPClient.OtherHeaders);
                    if(*SMTPClient.OtherHeaders == 0u)
                    {
                        TCPPutArray(MySocket, (uint8_t*)"\r\n", 2);
                        PutHeadersState = PUTHEADERS_DONE;
                        SMTPState++;
                    }
                    break;

                // Default case needed to supress compiler diagnostics
                default:
                    break;
                }
            }
            TCPFlush(MySocket);
            break;

        case SMTP_DATA_BODY_INIT:
            SMTPState++;
            RAMStrPtr = (uint8_t*)SMTPClient.Body;
            ROMStrPtr2 = (const uint8_t*)"\r\n.\r\n";
            CRPeriod.Pos = NULL;
            if(RAMStrPtr)
                CRPeriod.Pos = (uint8_t*)strstr((char*)RAMStrPtr, (const char*)"\r\n.");
        // No break here

        case SMTP_DATA_BODY:
            if(SMTPClient.Body)
            {
                if(*ROMStrPtr2)
                {
                    // Put the application data, doing the transparancy replacement of "\r\n." with "\r\n.."
                    while(CRPeriod.Pos)
                    {
                        CRPeriod.Pos += 3;
                        RAMStrPtr += TCPPutArray(MySocket, RAMStrPtr, CRPeriod.Pos-RAMStrPtr);
                        if(RAMStrPtr == CRPeriod.Pos)
                        {
                            if(!TCPPut(MySocket, '.'))
                            {
                                CRPeriod.Pos -= 3;
                                break;
                            }
                        }
                        else
                        {
                            CRPeriod.Pos -= 3;
                            break;
                        }
                        CRPeriod.Pos = (uint8_t*)strstr((char*)RAMStrPtr, (const char*)"\r\n.");
                    }

                    // If we get down here, either all replacements have been made or there is no remaining space in the TCP output buffer
                    RAMStrPtr = TCPPutString(MySocket, RAMStrPtr);
                    ROMStrPtr2 = TCPPutString(MySocket, (uint8_t*)ROMStrPtr2);
                    TCPFlush(MySocket);
                }
            }
            else
            {
                if(SMTPFlags.bits.ReadyToFinish)
                {
                    if(*ROMStrPtr2)
                    {
                        ROMStrPtr2 = TCPPutString(MySocket, (uint8_t*)ROMStrPtr2);
                        TCPFlush(MySocket);
                    }

                }
            }

            if(*ROMStrPtr2 == 0u)
            {
                SMTPState++;
            }
            break;

        case SMTP_QUIT_INIT:
            SMTPState++;
            ROMStrPtr = (const uint8_t*)"QUIT\r\n";
        // No break here

        case SMTP_QUIT:
            if(*ROMStrPtr)
            {
                ROMStrPtr = TCPPutString(MySocket, (uint8_t*)ROMStrPtr);
                TCPFlush(MySocket);
            }

            if(*ROMStrPtr == 0u)
            {
                TransportState = TRANSPORT_CLOSE;
            }
            break;

        // Default case needed to supress compiler diagnostics
        default:
            break;
        }
        break;

    case TRANSPORT_CLOSE:
        // Close the socket so it can be used by other modules
        TCPClose(MySocket);
        MySocket = INVALID_SOCKET;

        // Go back to doing nothing
        TransportState = TRANSPORT_HOME;
        break;
    }
}
コード例 #23
0
ファイル: dyn_dns.c プロジェクト: webgou/Equinox-Clock
/****************************************************************************
  Function:
    void DDNSTask(void)

  Summary:
    Dynamic DNS client task/state machine.

  Description:
  	This function performs the background tasks of the Dynamic DNS Client.
  	Once the DDNSPointers structure is configured, this task attempt to 
  	update the Dynamic DNS hostname on a periodic schedule.
  	
  	The task first accesses the CheckIP server to determine the device's
  	current external IP address.  If the IP address has changed, it 
  	issues an update command to the dynamic DNS service to propagate the
  	change.  This sequence executes whenever dwUpdateAt elapses, which by
  	default is every 10 minutes, or when an update is forced.
    
  Precondition:
    DDNSInit() has been called.

  Parameters:
	None
	
  Returns:
    None

  Remarks:
	This function acts as a task (similar to one in an RTOS).  It
	performs its task in a co-operative manner, and the main application
	must call this function periodically to ensure that its tasks get 
	executed in a timely fashion.
  ***************************************************************************/
void DDNSTask(void)
{
	uint8_t 				i;
	static SYS_TICK		DDnsTimer;
	static TCP_SOCKET	MySocket = INVALID_SOCKET;
	static char const * 	ROMStrPtr;
	static char * 		RAMStrPtr;

	static uint8_t vBuffer[16];
	uint16_t wPos;
	static IP_ADDR ipParsed;
	
	static enum
	{
		SM_IDLE = 0u,
		SM_BEGIN_CHECKIP,				//0x1
		SM_CHECKIP_SKT_OBTAINED,		//0x2
		SM_CHECKIP_FIND_DELIMITER,		//0x3
		SM_CHECKIP_FIND_ADDRESS,		//0x4
		SM_CHECKIP_DISCONNECT,			//0x5
		SM_IP_UPDATE_HOME,				//0x6
		SM_IP_UPDATE_SKT_OBTAINED,		//0x7

		/*  
			HTTP request msg is divided into 6 parts 
			SM_IP_UPDATE_REQ_A,B,C,D,E,F as the tcp ip tx
			buffer is only able to carry 200 bytes at a time.
		*/
		
		SM_IP_UPDATE_REQ_A,				//0x8
		SM_IP_UPDATE_REQ_B,				//0x9
		SM_IP_UPDATE_REQ_C,				//0xa	
		SM_IP_UPDATE_REQ_D,				//0xb
		SM_IP_UPDATE_REQ_E,				//0xc
		SM_IP_UPDATE_REQ_F,				//0xd

		SM_IPUPDATE_FIND_RESPONSE,		//0xe
		SM_IPUPDATE_PARSE_RESPONSE,		//0xf
		SM_IPUDATE_DISCONNECT,			//0x10
		SM_DONE,						// Done, try again in 10 minutes
		SM_SOFT_ERROR,					// Soft error, try again in 30 seconds
		SM_SYSTEM_ERROR 				// System error, try again in 30 minutes
	} smDDNS = SM_IDLE;

	switch(smDDNS)
	{
		case SM_IDLE:

			// Wait for timeout to begin IP check
			if(SYS_TICK_Get() > dwUpdateAt)
				break;
			
			// Otherwise, continue to next state
			smDDNS = SM_BEGIN_CHECKIP;
				
		case SM_BEGIN_CHECKIP:
			
			// If a fatal error has occurred, abort to the SM_DONE state and keep
			// the error message.
			if(lastStatus >= DDNS_STATUS_ABUSE && lastStatus <= DDNS_STATUS_911)
			{
				smDDNS = SM_DONE;
				break;
			}

			// If DDNSClient is not properly configured, abort
			if( 
				// Verify that each pointer is not null, and is not empty
				(DDNSClient.ROMPointers.Host && (!DDNSClient.Host.szROM || *DDNSClient.Host.szROM == '\0') ) ||
				(!DDNSClient.ROMPointers.Host && (!DDNSClient.Host.szRAM || *DDNSClient.Host.szRAM == '\0') ) ||
				(DDNSClient.ROMPointers.Username && (!DDNSClient.Username.szROM || *DDNSClient.Username.szROM == '\0') ) ||
				(!DDNSClient.ROMPointers.Username && (!DDNSClient.Username.szRAM || *DDNSClient.Username.szRAM == '\0') ) ||
				(DDNSClient.ROMPointers.Password && (!DDNSClient.Password.szROM || *DDNSClient.Password.szROM == '\0') ) ||
				(!DDNSClient.ROMPointers.Password && (!DDNSClient.Password.szRAM || *DDNSClient.Password.szRAM == '\0') ) ||
				(DDNSClient.ROMPointers.CheckIPServer && (!DDNSClient.CheckIPServer.szROM || *DDNSClient.CheckIPServer.szROM == '\0') ) ||
				(!DDNSClient.ROMPointers.CheckIPServer && (!DDNSClient.CheckIPServer.szRAM || *DDNSClient.CheckIPServer.szRAM == '\0') ) ||
				(DDNSClient.ROMPointers.UpdateServer && (!DDNSClient.UpdateServer.szROM || *DDNSClient.UpdateServer.szROM == '\0') ) ||
				(!DDNSClient.ROMPointers.UpdateServer && (!DDNSClient.UpdateServer.szRAM || *DDNSClient.UpdateServer.szRAM == '\0') )
			)
			{
				smDDNS = SM_SOFT_ERROR;
				lastStatus = DDNS_STATUS_INVALID;
				break;
			}
			
			// Start with an invalidated IP String
			vBuffer[0] = '\0';
	
			// Connect a socket to the remote server
			if(DDNSClient.ROMPointers.CheckIPServer)
			{	
				MySocket = TCPOpen((uint32_t)(PTR_BASE)DDNSClient.CheckIPServer.szROM, TCP_OPEN_ROM_HOST,
					DDNSClient.CheckIPPort, TCP_PURPOSE_DEFAULT);
			}
			else
			{
				MySocket = TCPOpen((uint32_t)(PTR_BASE)DDNSClient.CheckIPServer.szRAM, TCP_OPEN_RAM_HOST,
					DDNSClient.CheckIPPort, TCP_PURPOSE_DEFAULT);						
			}
			
			// If no socket available, try again on next loop
			if(MySocket == INVALID_SOCKET)
				break;

			smDDNS++;
			DDnsTimer = SYS_TICK_Get();
			break;

		case SM_CHECKIP_SKT_OBTAINED:

			// Wait for the remote server to accept our connection request
			if(!TCPIsConnected(MySocket))
			{
				// Time out if too much time is spent in this state
				if(SYS_TICK_Get()-DDnsTimer > 6*SYS_TICK_TicksPerSecondGet())
				{
					// Close the socket so it can be used by other modules
					// We will retry soon
					TCPDisconnect(MySocket);
					MySocket = INVALID_SOCKET;
					lastStatus = DDNS_STATUS_CHECKIP_ERROR;
					smDDNS = SM_SOFT_ERROR;
				}
				break;
			}

			DDnsTimer = SYS_TICK_Get();

			// Make certain the socket can be written to
			if(TCPIsPutReady(MySocket) < 125u)//125 = size of TCP Tx buffer
				break;
			
			// Transmit the request to the server
			TCPPutString(MySocket, (const uint8_t*)"GET / HTTP/1.0\r\nHost: ");

			if(DDNSClient.ROMPointers.CheckIPServer)
			{
				TCPPutString(MySocket, DDNSClient.CheckIPServer.szROM);
			}
			else
			{
				TCPPutString(MySocket, DDNSClient.CheckIPServer.szRAM);
			}

			TCPPutString(MySocket, (const uint8_t*)"\r\nConnection: close\r\n\r\n");

			// Send the packet
			TCPFlush(MySocket);
			smDDNS++;
			break;

		case SM_CHECKIP_FIND_DELIMITER:

			// Check if remote node is still connected.  If not, force to the disconnect state,
			// but don't break because data may still be waiting.
			if(!TCPIsConnected(MySocket) || SYS_TICK_Get() - DDnsTimer > 6*SYS_TICK_TicksPerSecondGet())
				smDDNS = SM_CHECKIP_DISCONNECT;

			// Search out the "Address: " delimiter in the response
			wPos = TCPFindArray(MySocket, (const uint8_t*)"Address: ", 9, 0, 0, false);
			
			// If not yet found, clear as much as possible and break
			if(wPos == 0xffff)
			{
				wPos = TCPIsGetReady(MySocket);
				if(wPos > 9u)
					TCPGetArray(MySocket, NULL, wPos - 9);
				break;
			}
				
			// Clear up to and past that string
			TCPGetArray(MySocket, NULL, wPos + 9);
		
			// Continue on to read the IP
			DDnsTimer = SYS_TICK_Get();
			smDDNS++;
		
		case SM_CHECKIP_FIND_ADDRESS:
			
			// Check if remote node is still connected.  If not, force to the disconnect state,
			// but don't break because data may still be waiting.
			if(!TCPIsConnected(MySocket) || SYS_TICK_Get() - DDnsTimer > 6*SYS_TICK_TicksPerSecondGet())
				smDDNS = SM_CHECKIP_DISCONNECT;

			// Search out the "</body>" delimiter in the response
			wPos = TCPFindArray(MySocket, (const uint8_t*)"</body>", 7, 0, 0, false);
			
			// If not yet found, break
			if(wPos == 0xffff)
				break;
				
			// Read and terminate that string as the IP address (preventing buffer overflows)
			if(wPos > 15u)
				wPos = 15;
			TCPGetArray(MySocket, vBuffer, wPos);
			vBuffer[wPos] = '\0';
			
			// Parse the IP address that was read, invalidating on failure
			if(!TCPIP_HELPER_StringToIPAddress((char*)vBuffer, &ipParsed))
				vBuffer[0] = '\0';

			// Continue on to close the socket			
			
		case SM_CHECKIP_DISCONNECT:

			// Close the socket
			TCPDisconnect(MySocket);
			MySocket = INVALID_SOCKET;

			// Determine if an update is necessary
			if(vBuffer[0] == '\0')
			{// CheckIP Failed
				lastStatus = DDNS_STATUS_CHECKIP_ERROR;
				smDDNS = SM_SOFT_ERROR;
				break;
			}

			if( (ipParsed.Val ==lastKnownIP.Val) && (!bForceUpdate))
			{
				// IP address has not changed and no update is forced
				lastStatus = DDNS_STATUS_UNCHANGED;
				smDDNS = SM_DONE;
				break;
			}
			
			// Need to perform an update
			lastKnownIP = ipParsed;
			bForceUpdate = false;
			smDDNS++;
			break;
			 
		case SM_IP_UPDATE_HOME:

			// Connect a socket to the remote server
			if(DDNSClient.ROMPointers.UpdateServer)
			{
				MySocket = TCPOpen((uint32_t)(PTR_BASE)DDNSClient.UpdateServer.szROM, TCP_OPEN_ROM_HOST, 
					DDNSClient.UpdatePort, TCP_PURPOSE_DEFAULT);
			}
			else
			{
				MySocket = TCPOpen((uint32_t)(PTR_BASE)DDNSClient.UpdateServer.szRAM, TCP_OPEN_RAM_HOST,
					DDNSClient.UpdatePort, TCP_PURPOSE_DEFAULT);
			}
	
			// If no socket is available, try again on the next loop
			if(MySocket == INVALID_SOCKET)
				break;
			
			// Move on to the next state
			smDDNS++;
			DDnsTimer = SYS_TICK_Get();
			break;

		case SM_IP_UPDATE_SKT_OBTAINED:
		
			// Wait for the remote server to accept our connection request
			if(!TCPIsConnected(MySocket))
			{
				// Time out if too much time is spent in this state
				if(SYS_TICK_Get() - DDnsTimer > 6*SYS_TICK_TicksPerSecondGet())
				{
					// Close the socket so it can be used by other modules
					// We will try again immediately
					TCPDisconnect(MySocket);
					MySocket = INVALID_SOCKET;
					lastStatus = DDNS_STATUS_UPDATE_ERROR;
					smDDNS--;
				}
				break;
			}
			
			// Reset timer and begin sending the request
			DDnsTimer = SYS_TICK_Get();
			smDDNS++;
			// No break needed...try to send first bit immediately.

		case SM_IP_UPDATE_REQ_A:
	
			// Check for lost connections or timeouts
			if(!TCPIsConnected(MySocket) || (SYS_TICK_Get() - DDnsTimer > 10*SYS_TICK_TicksPerSecondGet()))
			{
				lastStatus = DDNS_STATUS_UPDATE_ERROR;
				smDDNS = SM_IPUDATE_DISCONNECT;
				break;
			}
			
			if(TCPIsPutReady(MySocket) < 25u)  // 25 =~ 16+9
				break;

			TCPPutString(MySocket, (const uint8_t*)"GET /nic/update?hostname=");
			smDDNS++;
			// No break needed...try to send next bit immediately.
			
		case SM_IP_UPDATE_REQ_B:

			// Check for lost connections or timeouts
			if(!TCPIsConnected(MySocket) || (SYS_TICK_Get() - DDnsTimer > 10*SYS_TICK_TicksPerSecondGet()))
			{
				lastStatus = DDNS_STATUS_UPDATE_ERROR;
				smDDNS = SM_IPUDATE_DISCONNECT;
				break; 
			}

			// Try to write, verifying that space is available first
			if(DDNSClient.ROMPointers.Host)
			{
				if(TCPIsPutReady(MySocket) < strlen((const char*)DDNSClient.Host.szROM))
					break;
				TCPPutString(MySocket,DDNSClient.Host.szROM);
			}
			else
			{
				if(TCPIsPutReady(MySocket) < strlen((char*)DDNSClient.Host.szRAM))
					break;
				TCPPutString(MySocket,DDNSClient.Host.szRAM);
			}

			smDDNS++;
			// No break needed...try to send next bit immediately.
			
		case SM_IP_UPDATE_REQ_C:

			// Check for lost connections or timeouts
			if(!TCPIsConnected(MySocket) || SYS_TICK_Get() - DDnsTimer > 10*SYS_TICK_TicksPerSecondGet())
			{
				lastStatus = DDNS_STATUS_UPDATE_ERROR;
				smDDNS = SM_IPUDATE_DISCONNECT;
				break; 
			}

			if(TCPIsPutReady(MySocket) < 70u)
				break;
	
			TCPPutString(MySocket, (const uint8_t*)"&myip=");
			TCPPutString(MySocket, vBuffer);
			TCPPutString(MySocket, (const uint8_t*)"&wildcard=NOCHG&mx=NOCHG&backmx=NOCHG HTTP/1.0");	

			TCPFlush(MySocket);
			smDDNS++;
			// No break needed...try to send next bit immediately.

		case SM_IP_UPDATE_REQ_D:

			// Check for lost connections or timeouts
			if(!TCPIsConnected(MySocket) || SYS_TICK_Get() - DDnsTimer > 10*SYS_TICK_TicksPerSecondGet())
			{
				lastStatus = DDNS_STATUS_UPDATE_ERROR;
				smDDNS = SM_IPUDATE_DISCONNECT;
				break; 
			}
			
			if(TCPIsPutReady(MySocket) < 131u) // 131 =~ 8+23 + dynamic dns server hostname
				break;

			TCPPutString(MySocket, (const uint8_t*)"\r\nHost: ");//8
			
			if(DDNSClient.ROMPointers.UpdateServer)
				TCPPutString(MySocket,DDNSClient.UpdateServer.szROM);
			else
				TCPPutString(MySocket,DDNSClient.UpdateServer.szRAM);
			
			TCPPutString(MySocket, (const uint8_t*)"\r\nAuthorization: Basic ");//23

			TCPFlush(MySocket);
			smDDNS++;
			// No break needed...try to send the next bit immediately.

		case SM_IP_UPDATE_REQ_E:

			// Check for lost connections or timeouts
			if(!TCPIsConnected(MySocket) || SYS_TICK_Get() - DDnsTimer > 6*SYS_TICK_TicksPerSecondGet())
			{
				lastStatus = DDNS_STATUS_UPDATE_ERROR;
				smDDNS = SM_IPUDATE_DISCONNECT;
				break; 
			}
			
			// User name and passwords for DynDNS.org can each be up to 24 characters
			// Base64 encoded data is always at least 25% bigger than the original
			if(TCPIsPutReady(MySocket) < 100u)
				break;	

			if(DDNSClient.ROMPointers.Username)
			{
				ROMStrPtr = (const char*)DDNSClient.Username.szROM;
				wPos = strlen(ROMStrPtr);
			}
			else
			{
				RAMStrPtr = (char*)DDNSClient.Username.szRAM;
				wPos = strlen((char*)RAMStrPtr);
			}

			i = 0;
			while(wPos)
			{
				while(i < wPos && i < 3u)
				{
					if(DDNSClient.ROMPointers.Username)
						vBuffer[i] = *ROMStrPtr++;
					else
						vBuffer[i] = *RAMStrPtr++;
					i++;
				}
				wPos -= i; 				
										
				if(i == 3u)
				{
					Base64Encode(vBuffer, i, vBuffer, 4);
					TCPPutArray(MySocket, vBuffer, 4);
					i = 0;
				}
			}

			if(DDNSClient.ROMPointers.Password)
			{		
				ROMStrPtr = (const char*)DDNSClient.Password.szROM;
				wPos = strlen(ROMStrPtr);
			}
			else
			{
				RAMStrPtr = (char*)DDNSClient.Password.szRAM;
				wPos = strlen((char*)RAMStrPtr);
			}

		  	// Increment for the ':' separator and i for bytes left in username
		  	wPos += i + 1;
			
			vBuffer[i++] = ':';

			while(wPos)
			{
				while(i < wPos && i < 3u)
				{
					if(DDNSClient.ROMPointers.Password)
						vBuffer[i] = *ROMStrPtr++;
					else
						vBuffer[i] = *RAMStrPtr++;
					i++;
				}
				wPos -= i; 				
				Base64Encode(vBuffer, i, vBuffer, 4);
				TCPPutArray(MySocket, vBuffer, 4);
				i = 0;
			}
			
			TCPFlush(MySocket);
			smDDNS++;
			break;

			
		case SM_IP_UPDATE_REQ_F:

			// Check for lost connections or timeouts
			if(!TCPIsConnected(MySocket) || SYS_TICK_Get() - DDnsTimer > 10*SYS_TICK_TicksPerSecondGet())
			{
				lastStatus = DDNS_STATUS_UPDATE_ERROR;
				smDDNS = SM_IPUDATE_DISCONNECT;
				break; 
			}
			
			if(TCPIsPutReady(MySocket) < 50u)
				break;
			
			TCPPutString(MySocket, (const uint8_t*)"\r\nUser-Agent: Microchip - TCPIPSTACK - "TCPIP_STACK_VERSION"\r\n\r\n");
			TCPFlush(MySocket);
			smDDNS++;
			
			// Reset the timer to wait for a response
			DDnsTimer = SYS_TICK_Get();
			break;
								
		case SM_IPUPDATE_FIND_RESPONSE:
			// Locate the response string

			// Wait up to 10 seconds for a response
			if(SYS_TICK_Get() - DDnsTimer > 10*SYS_TICK_TicksPerSecondGet())
			{
				lastStatus = DDNS_STATUS_UPDATE_ERROR;
				smDDNS = SM_IPUDATE_DISCONNECT;
				break;
			}
		
			// According to HTTP, the response will start after the two CRLFs
			wPos = TCPFindArray(MySocket, (const uint8_t*)"\r\n\r\n", 4, 0, 0, false);

			// If not yet found, eliminate everything up to
			if(wPos == 0xffff)
			{
				wPos = TCPIsGetReady(MySocket);
				if(wPos > 4u)
					TCPGetArray(MySocket, NULL, wPos - 4);
				break;
			}
				
			TCPGetArray(MySocket, NULL, wPos+4);
			smDDNS++;
			// No break...continue to next state immediately
			
		case SM_IPUPDATE_PARSE_RESPONSE:
			// Try to parse the response text
			
			// Wait up to 10 seconds for the remote server to disconnect
			// so we know all data has been received
			if(TCPIsConnected(MySocket) && SYS_TICK_Get() - DDnsTimer < 10*SYS_TICK_TicksPerSecondGet())
				break;
			
			// Read the response code
		 	wPos = TCPIsGetReady(MySocket);
		 	if(wPos > sizeof(vBuffer) - 1)
		 		wPos = sizeof(vBuffer) - 1;

			wPos = TCPGetArray(MySocket, vBuffer, wPos);
			vBuffer[wPos] = '\0';
			for(i = 0; i < sizeof(vBuffer); i++)
				if(vBuffer[i] == ' ')
					vBuffer[i] = '\0';

			for(lastStatus = 0; lastStatus < DDNS_STATUS_UPDATE_ERROR; lastStatus++)
				if(!strcmp((char*)vBuffer, (const char*)_updateIpSrvrResponse[lastStatus]))
					break;
		
			smDDNS++;
			// No break...continue to finalization

		case SM_IPUDATE_DISCONNECT:
			// Close the socket so it can be used by other modules.
			if(MySocket != INVALID_SOCKET)
			{
				TCPDisconnect(MySocket);
				MySocket = INVALID_SOCKET;
			}
			
			// Determine what to do based on status
			if(lastStatus <= DDNS_STATUS_NUMHOST || lastStatus == DDNS_STATUS_UNCHANGED)
				smDDNS = SM_DONE;
			else if(lastStatus == DDNS_STATUS_911 || lastStatus == DDNS_STATUS_DNSERR)
				smDDNS = SM_SYSTEM_ERROR;
			else
				smDDNS = SM_SOFT_ERROR;
			
			smDDNS++;
			break;
			
		case SM_DONE:
			dwUpdateAt = SYS_TICK_Get() + 10*60*SYS_TICK_TicksPerSecondGet();	// 10 minutes
			smDDNS = SM_IDLE;
			break;
			
		case SM_SOFT_ERROR:
			dwUpdateAt = SYS_TICK_Get() + 30*SYS_TICK_TicksPerSecondGet(); 		// 30 seconds
			smDDNS = SM_IDLE;
			break;
					
		case SM_SYSTEM_ERROR:
			dwUpdateAt = SYS_TICK_Get() + 30*60*SYS_TICK_TicksPerSecondGet();		// 30 minutes
			smDDNS = SM_IDLE;
			break;
	}
}
コード例 #24
0
ファイル: main_demo.c プロジェクト: dakkanner/cst-417-lab
//
// Main application entry point.
//
int main(void)
{

#if defined(HOST_CM_TEST)
    DWORD t1 = 0;
    char st[80];
    BOOL host_scan = FALSE;
    UINT16 scan_count = 0;
#endif

    static IPV4_ADDR dwLastIP[sizeof (TCPIP_HOSTS_CONFIGURATION) / sizeof (*TCPIP_HOSTS_CONFIGURATION)];
    int i, nNets;

#if defined(SYS_USERIO_ENABLE)    
    static SYS_TICK startTick = 0;
    int32_t LEDstate=SYS_USERIO_LED_DEASSERTED;
#endif  // defined(SYS_USERIO_ENABLE)

    TCPIP_NET_HANDLE netH;
    const char  *netName=0;
    const char  *netBiosName;

#if defined (TCPIP_STACK_USE_ZEROCONF_MDNS_SD)
    char mDNSServiceName[] = "MyWebServiceNameX ";     // base name of the service Must not exceed 16 bytes long
                                                       // the last digit will be incremented by interface
#endif  // defined (TCPIP_STACK_USE_ZEROCONF_MDNS_SD)

    // perform system initialization
    if(!SYS_Initialize())
    {
        return 0;
    }


    SYS_CONSOLE_MESSAGE("\r\n\n\n ---  TCPIP Demo Starts!  --- \r\n");
    SYS_OUT_MESSAGE("TCPIPStack " TCPIP_STACK_VERSION "  ""                ");

    // Initialize the TCPIP stack
    if (!TCPIP_STACK_Init(TCPIP_HOSTS_CONFIGURATION, sizeof (TCPIP_HOSTS_CONFIGURATION) / sizeof (*TCPIP_HOSTS_CONFIGURATION),
            TCPIP_STACK_MODULE_CONFIG_TBL, sizeof (TCPIP_STACK_MODULE_CONFIG_TBL) / sizeof (*TCPIP_STACK_MODULE_CONFIG_TBL)))
    {
        return 0;
    }

    // Display the names associated with each interface
    // Perform mDNS registration if mDNS is enabled
    nNets = TCPIP_STACK_NetworksNo();
    for(i = 0; i < nNets; i++)
    {
        netH = TCPIP_STACK_IxToNet(i);
        netName = TCPIP_STACK_NetName(netH);
        netBiosName = TCPIP_STACK_NetBIOSName(netH);

#if defined(TCPIP_STACK_USE_NBNS)
        SYS_CONSOLE_PRINT("    Interface %s on host %s - NBNS enabled\r\n", netName, netBiosName);
#else
        SYS_CONSOLE_PRINT("    Interface %s on host %s - NBNS disabled\r\n", netName, netBiosName);
#endif  // defined(TCPIP_STACK_USE_NBNS)

#if defined (TCPIP_STACK_USE_ZEROCONF_MDNS_SD)
        mDNSServiceName[sizeof(mDNSServiceName) - 2] = '1' + i;
        mDNSServiceRegister( netH
            , mDNSServiceName                   // name of the service
            ,"_http._tcp.local"                 // type of the service
            ,80                                 // TCP or UDP port, at which this service is available
            ,((const BYTE *)"path=/index.htm")  // TXT info
            ,1                                  // auto rename the service when if needed
            ,NULL                               // no callback function
            ,NULL);                             // no application context
#endif //TCPIP_STACK_USE_ZEROCONF_MDNS_SD
    }

#if defined (TCPIP_STACK_USE_IPV6)
    TCPIP_ICMPV6_RegisterCallback(ICMPv6Callback);
#endif

#if defined(TCPIP_STACK_USE_ICMP_CLIENT)
    ICMPRegisterCallback(PingProcessIPv4);
#endif


#if defined(TCPIP_STACK_USE_EVENT_NOTIFICATION)
    TCPIP_NET_HANDLE hWiFi = TCPIP_STACK_NetHandle("MRF24W");
    if (hWiFi)
    {
       TCPIP_STACK_RegisterHandler(hWiFi, TCPIP_EV_RX_ALL | TCPIP_EV_TX_ALL | TCPIP_EV_RXTX_ERRORS, StackNotification, 0);
    }
#endif  // defined(TCPIP_STACK_USE_EVENT_NOTIFICATION)

#if defined(WF_UPDATE_FIRMWARE_UART_24G)
    extern bool    WF_FirmwareUpdate_Uart_24G(void);
    WF_FirmwareUpdate_Uart_24G();
#endif

  

    // Now that all items are initialized, begin the co-operative
    // multitasking loop.  This infinite loop will continuously
    // execute all stack-related tasks, as well as your own
    // application's functions.  Custom functions should be added
    // at the end of this loop.
    // Note that this is a "co-operative mult-tasking" mechanism
    // where every task performs its tasks (whether all in one shot
    // or part of it) and returns so that other tasks can do their
    // job.
    // If a task needs very long time to do its job, it must be broken
    // down into smaller pieces so that other tasks can have CPU time.
    while (1)
    {
        SYS_Tasks();

       
#if defined(SYS_USERIO_ENABLE)    
        // Blink LED0 (right most one) every second.
        if (SYS_TICK_Get() - startTick >= SYS_TICK_TicksPerSecondGet() / 2ul)
        {
            startTick = SYS_TICK_Get();
            LEDstate ^= SYS_USERIO_LED_ASSERTED;
            SYS_USERIO_SetLED(SYS_USERIO_LED_0, LEDstate);
        }
#endif  // defined(SYS_USERIO_ENABLE)   

        // This task performs normal stack task including checking
        // for incoming packet, type of packet and calling
        // appropriate stack entity to process it.
        TCPIP_STACK_Task();

        // Process application specific tasks here.
        // For this demo app, this will include the Generic TCP
        // client and servers, and the SNMP, Ping, and SNMP Trap
        // demos.  Following that, we will process any IO from
        // the inputs on the board itself.
        // Any custom modules or processing you need to do should
        // go here.
#if defined(TCPIP_STACK_USE_TCP) && defined(APP_USE_FTP_CLIENT_DEMO)
        FTPClient();
#endif        
#if defined(TCPIP_STACK_USE_TCP) && defined(APP_USE_GENERIC_TCP_CLIENT_DEMO)
        GenericTCPClient();
#endif

#if defined(TCPIP_STACK_USE_TCP) && defined(APP_USE_GENERIC_TCP_SERVER_DEMO)
        GenericTCPServer();
#endif

#if defined(TCPIP_STACK_USE_SMTP_CLIENT) && defined(APP_USE_SMTP_CLIENT_DEMO)
        SMTPDemo();
#endif

#if (defined(TCPIP_STACK_USE_ICMP_CLIENT) || defined (TCPIP_STACK_USE_IPV6)) && defined(APP_USE_PING_DEMO)
        // use ping on the default interface
        PingDemoTask();
#endif

#if defined(TCPIP_STACK_USE_SNMP_SERVER) && !defined(SNMP_TRAP_DISABLED)

        // User should use one of the following SNMP demo
        // This routine demonstrates V1 or V2 trap formats with one variable binding.

        //SNMPTrapDemo(); //This function sends the both SNMP trap version1 and 2 type of notifications

        #if defined(SNMP_STACK_USE_V2_TRAP) || defined(SNMP_V1_V2_TRAP_WITH_SNMPV3)
        //This routine provides V2 format notifications with multiple (3) variable bindings
        //User should modify this routine to send v2 trap format notifications with the required varbinds.
            SNMPV2TrapDemo(); //This function sends the SNMP trap version 2 type of notifications
        #endif

         /*
         SNMPSendTrap() is used to send trap notification to previously configured ip address if trap notification is enabled.
         There are different trap notification code. The current implementation sends trap for authentication failure (4).
           PreCondition: If application defined event occurs to send the trap. Declare a notification flag and update as the event occurs.
           Uncomment the below function if the application requires.

         if(notification flag is updated by the application as a predefined event occured)
        {
            SNMPSendTrap();
        }

        */

#endif 


#if defined(TCPIP_STACK_USE_BERKELEY_API) && defined(APP_USE_BERKELEY_API_DEMO)
        BerkeleyTCPClientDemo();
        BerkeleyTCPServerDemo();
        BerkeleyUDPClientDemo(0);
#endif

        // If the local IP address has changed (ex: due to DHCP lease change)
        // write the new IP address to the console display, UART, and Announce
        // service
        // We use the default interface
        for (i = 0; i < sizeof (TCPIP_HOSTS_CONFIGURATION) / sizeof (*TCPIP_HOSTS_CONFIGURATION); i++)
        {
            netH = TCPIP_STACK_NetHandle(TCPIP_HOSTS_CONFIGURATION[i].interface);
            if ((uint32_t) dwLastIP[i].Val != TCPIP_STACK_NetAddress(netH))
            {
                dwLastIP[i].Val = TCPIP_STACK_NetAddress(netH);

                SYS_CONSOLE_PRINT("Interface Name is: %s\r\n", TCPIP_HOSTS_CONFIGURATION[i].interface);
                SYS_CONSOLE_MESSAGE("New IP Address is: "); DisplayIPValue(dwLastIP[i]);
                SYS_CONSOLE_MESSAGE("\r\n");
            }
        }

#if defined(TCPIP_STACK_USE_EVENT_NOTIFICATION)
        if (stackNotifyCnt)
        {
            stackNotifyCnt = 0;
            ProcessNotification(stackNotifyHandle);
        }
#endif  // defined(TCPIP_STACK_USE_EVENT_NOTIFICATION)

#if defined(WF_UPDATE_FIRMWARE_TCPCLIENT_24G)
    void WF_FirmwareUpdate_TcpClient_24G(void);
    WF_FirmwareUpdate_TcpClient_24G();
#endif //defined(WF_UPDATE_FIRMWARE_TCPCLIENT_24G)

#if defined(HOST_CM_TEST)
       switch (g_event)
        {
            case WF_EVENT_CONNECTION_PERMANENTLY_LOST:
            case WF_EVENT_CONNECTION_FAILED:
                g_event = 0xff;             // clear current event
                // if host scan is active, it can be forced inactive by connection/re-connection process
                // so just reset host scan state to inactive.
                host_scan = FALSE;          // host scan inactive
                SYS_CONSOLE_MESSAGE("Reconnecting....\r\n");
                WF_Connect();
                break;
            case WF_EVENT_CONNECTION_SUCCESSFUL:
                g_event = 0xff;             // clear current event
                // if host scan is active, it can be forced inactive by connection/re-connection process
                // so just reset host scan state to inactive.
                host_scan = FALSE;          // host scan inactive
                break;
            case WF_EVENT_SCAN_RESULTS_READY:
                g_event = 0xff;             // clear current event
                host_scan = FALSE;          // host scan inactive
                // Scan results are valid - OK to retrieve
                if (SCANCXT.numScanResults > 0)
                {
                    SCAN_SET_DISPLAY(SCANCXT.scanState);
                    SCANCXT.displayIdx = 0;
                    while (IS_SCAN_STATE_DISPLAY(SCANCXT.scanState))
                         WFDisplayScanMgr();
                }
                break;
           case WF_EVENT_CONNECTION_TEMPORARILY_LOST:
                // This event can happened when CM in module is enabled.
                g_event = 0xff;         // clear current event
                // if host scan is active, it can be forced inactive by connection/re-connection process
                // so just reset host scan state to inactive.
                host_scan = FALSE;      // host scan inactive
                break;
            default:
                //sprintf(st,"skip event = %d\r\n",g_event);
                //SYS_CONSOLE_MESSAGE(st);
                break;
        }

       if (g_DhcpSuccessful)
       {

       /* Send and Receive UDP packets */
        if(UDPIsOpened(socket1))
        {
            // UDP TX every 10 msec
            if(SYS_TICK_Get() - timeudp >= SYS_TICK_TicksPerSecondGet() / 100)
            {
                timeudp = SYS_TICK_Get();
                tx_number++;
                LED0_IO ^= 1;
                sprintf(str,"rem=%12lu",tx_number);
                for(cntstr=16;cntstr<999;cntstr++)
                    str[cntstr]=cntstr;
                str[999]=0;
                // Send tx_number (formatted in a string)
                if(UDPIsTxPutReady(socket1,1000)!=0)
                {
                    UDPPutString(socket1,(BYTE *)str);
                    UDPFlush(socket1);
                    SYS_CONSOLE_MESSAGE(".");
                }
            }

            // UDP RX tx_number of remote board
            if(UDPIsGetReady(socket1)!=0)
            {
                LED1_IO ^= 1;
                UDPGetArray(socket1,(BYTE *)str,1000);
                str[16]=0;
                //sprintf((char*)LCDText,"%sloc=%12lu",str,tx_number); // Write on EXP16 LCD local and remote TX number
                //strcpypgm2ram(LCDText,str);
                //LCDUpdate();
                SYS_CONSOLE_MESSAGE("Rx");

            }
        }

        // Do host scan
         if((SYS_TICK_Get() - t1) >= SYS_TICK_TicksPerSecondGet() * 20)
        {
            t1 = SYS_TICK_Get();
            if (!host_scan)             // allow host scan if currently inactive
            {
                sprintf(st,"%d Scanning ..... event = %d\r\n",++scan_count, g_event);
                SYS_CONSOLE_MESSAGE(st);
                host_scan = TRUE;       // host scan active
                WF_Scan(0xff);          // scan on all channels
            }
        }
       } // DHCP status
       
#endif  //HOST_CM_TEST


    }
}
コード例 #25
0
//
// Main application entry point.
//
int main(void)
{

#if defined(APP_USE_IPERF)
    static uint8_t iperfOk = 0;
#endif
    static SYS_TICK startTick = 0;
    static IP_ADDR dwLastIP[sizeof (TCPIP_HOSTS_CONFIGURATION) / sizeof (*TCPIP_HOSTS_CONFIGURATION)];
    uint8_t i;


    // perform system initialization
    if(!SYS_Initialize())
    {
        return 0;
    }

    SYS_CONSOLE_MESSAGE("\r\n\n\n --- Unified TCPIP Demo Starts! --- \r\n");

    SYS_OUT_MESSAGE("TCPStack " TCPIP_STACK_VERSION "  ""                ");

    #if defined(TCPIP_STACK_USE_MPFS) || defined(TCPIP_STACK_USE_MPFS2)
	MPFSInit();
	#endif

    // Initiates board setup process if button is depressed 
	// on startup
    if(BUTTON0_IO == 0u)
    {
        #if defined(TCPIP_STACK_USE_STORAGE)  && (defined(SPIFLASH_CS_TRIS) || defined(EEPROM_CS_TRIS))
		// Invalidate the EEPROM contents if BUTTON0 is held down for more than 4 seconds
		SYS_TICK StartTime = SYS_TICK_Get();
		LED_PUT(0x00);
				
		while(BUTTON0_IO == 0u)
		{
			if(SYS_TICK_Get() - StartTime > 4*SYS_TICK_TicksPerSecondGet())
			{
                TCPIP_STORAGE_HANDLE hStorage;
                
                // just in case we execute this before the stack is initialized
                TCPIP_STORAGE_Init(0);
                hStorage = TCPIP_STORAGE_Open(0, false);   // no refresh actually needed
                if(hStorage)
                {
                    TCPIP_STORAGE_Erase(hStorage);
                    SYS_CONSOLE_MESSAGE("\r\n\r\nBUTTON0 held for more than 4 seconds.  Default settings restored.\r\n\r\n");
                    TCPIP_STORAGE_Close(hStorage);
                }
                else
                {
                    SYS_ERROR(SYS_ERROR_WARN, "\r\n\r\nCould not restore the default settings!!!.\r\n\r\n");
                }
                TCPIP_STORAGE_DeInit(0);
                
				LED_PUT(0x0F);
                // wait 4.5 seconds here then reset
				while((SYS_TICK_Get() - StartTime) <= (9*SYS_TICK_TicksPerSecondGet()/2));
				LED_PUT(0x00);
				while(BUTTON0_IO == 0u);
				SYS_Reboot();
				break;
			}
		}
        #endif  // defined(TCPIP_STACK_USE_STORAGE)  && (defined(SPIFLASH_CS_TRIS) || defined(EEPROM_CS_TRIS))
    }

    // Initialize the TCPIP stack
    if(!TCPIP_STACK_Init(TCPIP_HOSTS_CONFIGURATION, sizeof(TCPIP_HOSTS_CONFIGURATION)/sizeof(*TCPIP_HOSTS_CONFIGURATION),
                       TCPIP_STACK_MODULE_CONFIG_TBL, sizeof(TCPIP_STACK_MODULE_CONFIG_TBL)/sizeof(*TCPIP_STACK_MODULE_CONFIG_TBL) ))
    {
        return 0;
    }
#if defined(TCPIP_STACK_USE_TELNET_SERVER)
    TelnetRegisterCallback(ProcessIO);
#endif  // defined(TCPIP_STACK_USE_TELNET_SERVER)

#if defined (TCPIP_STACK_USE_IPV6)
    TCPIP_ICMPV6_RegisterCallback (ICMPv6Callback);
#endif

#if defined(TCPIP_STACK_USE_ICMP_CLIENT) || defined(TCPIP_STACK_USE_ICMP_SERVER)
    ICMPRegisterCallback (PingProcessIPv4);
#endif


#if defined(TCPIP_STACK_USE_EVENT_NOTIFICATION)
    TCPIP_NET_HANDLE hWiFi = TCPIP_STACK_NetHandle("MRF24W");
    if(hWiFi)
    {
        TCPIP_STACK_SetNotifyEvents(hWiFi, TCPIP_EV_RX_ALL|TCPIP_EV_TX_ALL|TCPIP_EV_RXTX_ERRORS);
        TCPIP_STACK_SetNotifyHandler(hWiFi, StackNotification, 0);
    }
#endif  // defined(TCPIP_STACK_USE_EVENT_NOTIFICATION)


#if defined(APP_USE_IPERF)
    IperfConsoleInit();
    iperfOk = IperfAppInit(TCPIP_HOSTS_CONFIGURATION[0].interface);
#endif

	// Now that all items are initialized, begin the co-operative
	// multitasking loop.  This infinite loop will continuously 
	// execute all stack-related tasks, as well as your own
	// application's functions.  Custom functions should be added
	// at the end of this loop.
    // Note that this is a "co-operative mult-tasking" mechanism
    // where every task performs its tasks (whether all in one shot
    // or part of it) and returns so that other tasks can do their
    // job.
    // If a task needs very long time to do its job, it must be broken
    // down into smaller pieces so that other tasks can have CPU time.
    while(1)
    {
        // Blink LED0 (right most one) every second.
        if(SYS_TICK_Get() - startTick >= SYS_TICK_TicksPerSecondGet()/2ul)
        {
            startTick = SYS_TICK_Get();
            LED0_IO ^= 1;
        }

        // This task performs normal stack task including checking
        // for incoming packet, type of packet and calling
        // appropriate stack entity to process it.
        TCPIP_STACK_Task();


		// Process application specific tasks here.
		// For this demo app, this will include the Generic TCP 
		// client and servers, and the SNMP, Ping, and SNMP Trap
		// demos.  Following that, we will process any IO from
		// the inputs on the board itself.
		// Any custom modules or processing you need to do should
		// go here.
		#if defined(TCPIP_STACK_USE_GENERIC_TCP_CLIENT_EXAMPLE)
		GenericTCPClient();
		#endif
		
		#if defined(TCPIP_STACK_USE_GENERIC_TCP_SERVER_EXAMPLE)
		GenericTCPServer();
		#endif
		
		#if defined(TCPIP_STACK_USE_SMTP_CLIENT)
		SMTPDemo();
		#endif
		
		#if defined(TCPIP_STACK_USE_ICMP_CLIENT) || defined (TCPIP_STACK_USE_ICMP_SERVER) || defined (TCPIP_STACK_USE_IPV6)
        // use ping on the default interface
		PingDemoTask();
		#endif
		
		#if defined(TCPIP_STACK_USE_SNMP_SERVER) && !defined(SNMP_TRAP_DISABLED)
		//User should use one of the following SNMP demo
		// This routine demonstrates V1 or V2 trap formats with one variable binding.
		SNMPTrapDemo();
		
		#if defined(SNMP_STACK_USE_V2_TRAP) || defined(SNMP_V1_V2_TRAP_WITH_SNMPV3)
		//This routine provides V2 format notifications with multiple (3) variable bindings
		//User should modify this routine to send v2 trap format notifications with the required varbinds.
		//SNMPV2TrapDemo();
		#endif 
		if(gSendTrapFlag)
			SNMPSendTrap();
		#endif
		
		#if defined(TCPIP_STACK_USE_BERKELEY_API)
		BerkeleyTCPClientDemo();
		BerkeleyTCPServerDemo();
		BerkeleyUDPClientDemo(0);
		#endif


#if defined(APP_USE_IPERF)
        IperfConsoleProcess();
        if (iperfOk) IperfAppCall();    // Only running in case of init succeed
        IperfConsoleProcessEpilogue();
#endif

        // If the local IP address has changed (ex: due to DHCP lease change)
        // write the new IP address to the console display, UART, and Announce
        // service
        // We use the default interface
        for (i = 0; i < sizeof(TCPIP_HOSTS_CONFIGURATION)/sizeof(*TCPIP_HOSTS_CONFIGURATION); i++)
        {	
            TCPIP_NET_HANDLE netH = TCPIP_STACK_NetHandle(TCPIP_HOSTS_CONFIGURATION[i].interface);
			if((uint32_t)dwLastIP[i].Val != TCPIP_STACK_NetAddress(netH))
			{
				dwLastIP[i].Val = TCPIP_STACK_NetAddress(netH);
				
				SYS_CONSOLE_MESSAGE(TCPIP_HOSTS_CONFIGURATION[i].interface);
				SYS_CONSOLE_MESSAGE(" new IP Address: ");
			
				DisplayIPValue(dwLastIP[i]);
			
				SYS_CONSOLE_MESSAGE("\r\n");
			
            }
        }

#if defined(TCPIP_STACK_USE_EVENT_NOTIFICATION)
        if(stackNotifyCnt)
        {
            stackNotifyCnt = 0;
            ProcessNotification(stackNotifyHandle);
        }
#endif  // defined(TCPIP_STACK_USE_EVENT_NOTIFICATION)
	}
}
コード例 #26
0
bool    WF_FirmwareUpdate_Uart_24G(void)
{
    enum SM_FIRMWARE_UPDATE
    {
        SM_FIRMWARE_UPDATE_SOH,
        SM_FIRMWARE_UPDATE_BLOCK,
        SM_FIRMWARE_UPDATE_BLOCK_CMP,
        SM_FIRMWARE_UPDATE_DATA,
        SM_FIRMWARE_UPDATE_CHECKSUM,
        SM_FIRMWARE_UPDATE_FINISH,
    } state;

    BYTE c;
   // MPFS_HANDLE handle;
    BOOL lbDone;
    BYTE blockLen=0;
    BOOL lResult = FALSE;
    BYTE BlockNumber=0, preBlockNum=0;
    BYTE checksum=0;
    
    SYS_TICK lastTick;
    SYS_TICK currentTick;
    state = SM_FIRMWARE_UPDATE_SOH;
    lbDone = FALSE;

    TCPIP_NET_HANDLE netH;
    netH = TCPIP_STACK_NetHandle("MRF24W");
    
    if( BUTTON3_IO == 1u) return FALSE;    
    printf("\n\rPress S2 (on Explorer16) to start the update.\n\r");
    while(BUTTON2_IO == 1u);
	printf("1\n");
    WF_Init(netH);//MACInit();
    printf("2\n");
    SYS_TICK_MsDelay(100);
	printf("3\n");
    AutoUpdate_Initialize();
    printf("I am ready, Please transfer firmware patch by XMODEM.\r\n"); 
    printf("If you press S3(On Explorwe16), I will stop update, and restore back to previous firmware.\r\n"); 
    lastTick = SYS_TICK_Get();
    do
    {
        currentTick = SYS_TICK_Get();
        if ( currentTick - lastTick >= (SYS_TICK_TicksPerSecondGet()*2) )
        {
            lastTick = SYS_TICK_Get();
            //todo jw  //while(BusyUART());
            _SYS_CONSOLE_PUTC(XMODEM_NAK); //WriteUART(XMODEM_NAK);
        }

    } while(!_SYS_CONSOLE_DATA_RDY()); //(!DataRdyUART());

    
    while(!lbDone)
    {
        if (BUTTON3_IO == 0u)   // If you want to cancel AutoUpdate, please press S3
        {
            printf("You press S3 button, revert begin...\r\n");
            AutoUpdate_Restore();
            printf("revert done\r\n");
            return FALSE;
        }
        if(_SYS_CONSOLE_DATA_RDY()) //(DataRdyUART())
        {
            c = _SYS_CONSOLE_GETC();//ReadUART();
            lastTick = SYS_TICK_Get();
        }
        else
        {
            // put some timeout to make sure  that we do not wait forever.
             currentTick = SYS_TICK_Get();
            if ( currentTick - lastTick >= (SYS_TICK_TicksPerSecondGet()*10) )
            {
                //if time out, copy old patch image from bank2 to bank1
                printf("timeout, revert begin...\r\n");
                AutoUpdate_Restore();
                printf("revert done\r\n");
                return FALSE;
            }
            continue;
        }
        //dbgPrintf("(%02x) ",c); 
        switch(state)
        {
        case SM_FIRMWARE_UPDATE_SOH:
            if(c == XMODEM_SOH)
            {
                state = SM_FIRMWARE_UPDATE_BLOCK;
                dbgPrintf("\r\n! ");
                checksum = c;
                lResult = TRUE;
            }
            else if ( c == XMODEM_EOT )
            {
                state = SM_FIRMWARE_UPDATE_FINISH;
                
                // todo jw://while(BusyUART());
                _SYS_CONSOLE_PUTC(XMODEM_ACK); //WriteUART(XMODEM_ACK);
                lbDone = TRUE;
            }  
            else
            {
                dbgPrintf("\n!error\n");
                while(1);
            }
            break;
        case SM_FIRMWARE_UPDATE_BLOCK:
            BlockNumber = c;
            dbgPrintf("BLK=%d ",BlockNumber);         
            checksum += c;
            state = SM_FIRMWARE_UPDATE_BLOCK_CMP;
            break;

        case SM_FIRMWARE_UPDATE_BLOCK_CMP:
            dbgPrintf("%d ",c);
            dbgPrintf("@:");
            //Judge: Is it correct ?
            if(c != (BlockNumber ^ 0xFF))
            {
                lResult = FALSE;
                dbgPrintf("\nBLOCK_CMP err: %x,%x\n", c, BlockNumber ^ 0xFF );
            }
            else 
            {
                if((BYTE)(preBlockNum+1) != BlockNumber)
                {
                    lResult = FALSE;
                    dbgPrintf("\nBLOCK  err %x %x\n",preBlockNum+1,BlockNumber);
                }
            }
            checksum += c;
            blockLen = 0;
            state = SM_FIRMWARE_UPDATE_DATA;
            break;
        case SM_FIRMWARE_UPDATE_DATA:
            // Buffer block data until it is over.
            tempData[blockLen++] = c;
            if ( blockLen == XMODEM_BLOCK_LEN )
            {
                state = SM_FIRMWARE_UPDATE_CHECKSUM;
            }
            checksum += c;
            
            break;
        case SM_FIRMWARE_UPDATE_CHECKSUM:
            dbgPrintf("Checksum=%x=%x ",checksum,c);
            if(checksum != c)
            {
                lResult = FALSE;
                dbgPrintf("\nchecksum  err\n");
            }
            XMODEM_SendToModule(tempData);
            // todo jw://while(BusyUART());
            if(lResult == TRUE)
            {
                _SYS_CONSOLE_PUTC(XMODEM_ACK);//WriteUART(XMODEM_ACK);
                preBlockNum++;
            }
            else
            {
                _SYS_CONSOLE_PUTC(XMODEM_NAK);//WriteUART(XMODEM_NAK);
            }
            state = SM_FIRMWARE_UPDATE_SOH;
            break;

        default:
            dbgPrintf("\n!error\n");
            while(1);
            break;
        }

    }
    
    AutoUpdate_Completed();

    return TRUE;
}
コード例 #27
0
ファイル: sntp.c プロジェクト: ctapang/v0_70_01b
// sntp_manager.h
bool TCPIP_SNTP_Client(TCPIP_NET_IF* pNetIf)
{
    NTP_PACKET          pkt;
    uint16_t            w;
    DNS_RESULT          dnsRes;
    static SYS_TICK     SNTPTimer;

    if(pSntpIf != 0 && pNetIf != pSntpIf)
    {   // not our job
        return false;
    }

    switch(sntpState)
    {
        case SM_HOME:
            sntpSocket = INVALID_UDP_SOCKET;
            pSntpIf = pSntpDefIf;
            if(!TCPIP_STACK_NetworkIsLinked(pSntpIf))
            {
                pSntpIf = _TCPIPStackAnyNetLinked(true);
            }

            if(TCPIP_DNS_UsageBegin(pSntpIf) != DNS_RES_OK)
            {
                ntpLastError = SNTP_RES_NTP_DNS_ERR; 
                break;
            }
            TCPIP_DNS_Resolve(NTP_SERVER, ntpConnection ==IP_ADDRESS_TYPE_IPV6 ? DNS_TYPE_AAAA : DNS_TYPE_A);
            sntpState++;
            break;

        case SM_WAIT_DNS:

            dnsRes = TCPIP_DNS_IsResolved(NTP_SERVER, &serverIP);
            if(dnsRes == DNS_RES_PENDING)
            {   // ongoing operation;
                break;
            }
            else if(dnsRes < 0)
            {   // some DNS error occurred; retry after waiting a while
                SNTPTimer = SYS_TICK_Get();
                sntpState = SM_SHORT_WAIT;
                ntpLastError = SNTP_RES_NTP_DNS_ERR; 
            }
            else
            {
                sntpState++;
            }
            TCPIP_DNS_UsageEnd(pSntpIf);
            break;

        case SM_DNS_RESOLVED:

            sntpSocket = TCPIP_UDP_ClientOpen(ntpConnection, NTP_SERVER_PORT, &serverIP);
            if(sntpSocket != INVALID_UDP_SOCKET)
            {
                TCPIP_UDP_SocketNetSet(sntpSocket, pSntpIf);
                sntpState++;
                SNTPTimer = SYS_TICK_Get();
            }
            else
            {
                ntpLastError = SNTP_RES_SKT_ERR; 
            }
            break;

        case SM_UDP_IS_OPENED:
            if(TCPIP_UDP_IsOpened(sntpSocket) == true)
            {
                SNTPTimer = SYS_TICK_Get();
                sntpState = SM_UDP_SEND;
            }
            else if((SYS_TICK_Get() - SNTPTimer > 1*SYS_TICK_TicksPerSecondGet()))
            {   // failed to open
                TCPIP_UDP_Close(sntpSocket);
                sntpState = SM_DNS_RESOLVED;
                sntpSocket = INVALID_UDP_SOCKET;
                ntpLastError = SNTP_RES_SKT_ERR; 
            }
            break;

        case SM_UDP_SEND:
            // Open up the sending UDP socket
            // Make certain the socket can be written to
            if(!TCPIP_UDP_TxPutIsReady(sntpSocket, sizeof(pkt)))
            {   // Wait no more than 1 sec
                if((SYS_TICK_Get() - SNTPTimer > 1*SYS_TICK_TicksPerSecondGet()))
                {
                    TCPIP_UDP_Close(sntpSocket);
                    sntpState = SM_DNS_RESOLVED;
                    sntpSocket = INVALID_UDP_SOCKET;
                    ntpLastError = SNTP_RES_SKT_ERR; 
                    break;
                }
            }

            // Success
            // Transmit a time request packet
            memset(&pkt, 0, sizeof(pkt));
            pkt.flags.versionNumber = NTP_VERSION;
            pkt.flags.mode = 3;             // NTP Client
            pkt.orig_ts_secs = TCPIP_Helper_htonl(NTP_EPOCH);
            TCPIP_UDP_ArrayPut(sntpSocket, (uint8_t*) &pkt, sizeof(pkt));
            TCPIP_UDP_Flush(sntpSocket);

            SNTPTimer = SYS_TICK_Get();
            sntpState = SM_UDP_RECV;
            break;

        case SM_UDP_RECV:
            // Look for a response time packet
            if(!TCPIP_UDP_GetIsReady(sntpSocket))
            {
                if((SYS_TICK_Get()) - SNTPTimer > NTP_REPLY_TIMEOUT * SYS_TICK_TicksPerSecondGet())
                {
                    // Abort the request and resume
                    TCPIP_UDP_Close(sntpSocket);
                    //SNTPTimer = SYS_TICK_Get();
                    //sntpState = SM_SHORT_WAIT;
                    sntpState = SM_HOME;
                    sntpSocket = INVALID_UDP_SOCKET;
                    ntpLastError = SNTP_RES_NTP_SERVER_TMO; 
                }
                break;
            }

            // Get the response time packet
            w = TCPIP_UDP_ArrayGet(sntpSocket, (uint8_t*) &pkt, sizeof(pkt));
            TCPIP_UDP_Close(sntpSocket);
            SNTPTimer = SYS_TICK_Get();
            sntpState = SM_WAIT;
            sntpSocket = INVALID_UDP_SOCKET;

            // sanity packet check
            if(w != sizeof(pkt) || pkt.flags.versionNumber != NTP_VERSION )
            {
                ntpLastError = SNTP_RES_NTP_VERSION_ERR; 
                break;
            }
            if((pkt.tx_ts_secs == 0 && pkt.tx_ts_fraq == 0))
            {
                ntpLastError = SNTP_RES_NTP_TSTAMP_ERR; 
                break;
            }
            if(pkt.stratum == 0 )
            {
                ntpLastError = SNTP_RES_NTP_KOD_ERR; 
                break;
            }
            if(pkt.stratum >= NTP_MAX_STRATUM || pkt.flags.leapIndicator == 3 )
            {
                ntpLastError = SNTP_RES_NTP_SYNC_ERR; 
                break;
            }

            // get the last timestamp
            ntpTimeStamp.tStampSeconds = pkt.tx_ts_secs;
            ntpTimeStamp.tStampFraction = pkt.tx_ts_fraq;
            ntpLastStampTick = SYS_TICK_Get();
            
            // Set out local time to match the returned time
            dwLastUpdateTick = ntpLastStampTick;
            dwSNTPSeconds = TCPIP_Helper_ntohl(pkt.tx_ts_secs) - NTP_EPOCH;
            // Do rounding.  If the partial seconds is > 0.5 then add 1 to the seconds count.
            if(((uint8_t*)&pkt.tx_ts_fraq)[0] & 0x80)
                dwSNTPSeconds++;

            break;

        case SM_SHORT_WAIT:
            // Attempt to requery the NTP server after a specified NTP_FAST_QUERY_INTERVAL time (ex: 8 seconds) has elapsed.
            if(SYS_TICK_Get() - SNTPTimer > (NTP_FAST_QUERY_INTERVAL * SYS_TICK_TicksPerSecondGet()))
            {
                sntpState = SM_HOME;
                sntpSocket = INVALID_UDP_SOCKET;
            }
            break;

        case SM_WAIT:
            // Requery the NTP server after a specified NTP_QUERY_INTERVAL time (ex: 10 minutes) has elapsed.
            if(SYS_TICK_Get() - SNTPTimer > (NTP_QUERY_INTERVAL * SYS_TICK_TicksPerSecondGet()))
            {
                sntpState = SM_HOME;
                sntpSocket = INVALID_UDP_SOCKET;
            }

            break;
    }

    return true;

}//TCPIP_SNTP_Client
コード例 #28
0
ファイル: auto_ip.c プロジェクト: webgou/Equinox-Clock
void AutoIPTasks(NET_CONFIG* pConfig)
{
//    uint8_t i;
    TCPIP_MAC_HANDLE hMac;

//    for (i = 0; i < NETWORK_INTERFACES; i++)
    {
        LoadState(_TCPIPStackNetIx(pConfig));
        hMac = _TCPIPStackNetToMac(pConfig);
        AutoIPClient.flags.bits.bCurrentLinkState = MACIsLinked(hMac);
    	if(AutoIPClient.flags.bits.bCurrentLinkState != AutoIPClient.flags.bits.bLastLinkState)
    	{
    		AutoIPClient.flags.bits.bLastLinkState = AutoIPClient.flags.bits.bCurrentLinkState;
    		if(!AutoIPClient.flags.bits.bCurrentLinkState)
    		{
                AutoIPClient.flags.bits.bConfigureAutoIP = false;
                AutoIPClient.smAUTOIPState = SM_AUTOIP_DISABLED;
    			pConfig->MyIPAddr.Val = pConfig->DefaultIPAddr.Val;
    			pConfig->MyMask.Val = pConfig->DefaultMask.Val;
    		}
            else
            {
                AutoIPClient.smAUTOIPState = SM_AUTOIP_INIT_RNG;
            }
    	}
    
        #if defined (TCPIP_STACK_USE_DHCP_CLIENT)
        if (DHCPIsBound(pConfig))
        {
            AutoIPClient.flags.bits.bConfigureAutoIP = false;
            AutoIPClient.smAUTOIPState = SM_AUTOIP_DISABLED;
            AutoIPClient.flags.bits.bLastDHCPState = true;
        }
        else
        {
            if (AutoIPClient.flags.bits.bLastDHCPState == true)
            {
                if (AutoIPClient.flags.bits.bCurrentLinkState)
                    AutoIPClient.smAUTOIPState = SM_AUTOIP_INIT_RNG;
            }
            AutoIPClient.flags.bits.bLastDHCPState = false;
        }
        #endif
    
    
        if (AutoIPClient.flags.bits.gDisableAutoIP == true)
        {
            AutoIPClient.flags.bits.bConfigureAutoIP = false;
            AutoIPClient.smAUTOIPState = SM_AUTOIP_DISABLED;
        }
    
    
        switch (AutoIPClient.smAUTOIPState)
        {
            // Default no-AutoIP case
        	case SM_AUTOIP_DISABLED:

                break;
    
            // Initializes the random number generator with a seed based on the MAC address
            case SM_AUTOIP_INIT_RNG:
                AutoIPRandSeed (((uint32_t)pConfig->MyMACAddr.v[0] + ((uint32_t)pConfig->MyMACAddr.v[1] << 8) + \
                        ((uint32_t)pConfig->MyMACAddr.v[2] << 16) + ((uint32_t)pConfig->MyMACAddr.v[3] << 24) + \
                        ((uint32_t)pConfig->MyMACAddr.v[4]) + ((uint32_t)pConfig->MyMACAddr.v[5] << 8)), pConfig);
    
                AutoIPClient.smAUTOIPState = SM_AUTOIP_CHECK_ADDRESS;
    
            // Check the address to see if it's in use before we write it into NetConfig
            case SM_AUTOIP_CHECK_ADDRESS:
    
                if (AutoIPClient.flags.bits.checkAddress == false)
                {
                    AutoIPClient.flags.bits.checkAddress = true;
    
                    pConfig->MyMask.Val = 0x00000000;
    
                    // Generate a random IP address (based on the MAC address) to try and claim.
                    // Dynamic link-local addresses can fall within the range:
                    // 169.254.1.0 - 169.254.254.255
                    AutoIPClient.packet.TargetIPAddr.byte.MB = AutoIPRand(pConfig) % 256;
                    AutoIPClient.packet.TargetIPAddr.byte.UB = (AutoIPRand(pConfig) % 254) + 1;
                    AutoIPClient.packet.TargetIPAddr.word.LW = 0xFEA9;
    
                    ARPResolve (pConfig, &AutoIPClient.packet.TargetIPAddr);
    
                    AutoIPClient.eventTime = SYS_TICK_Get();
                }
                
                if (!ARPIsResolved (pConfig, &AutoIPClient.packet.TargetIPAddr, &AutoIPClient.packet.TargetMACAddr))
                {
                    if (SYS_TICK_Get() - AutoIPClient.eventTime > SYS_TICK_TicksPerSecondGet())
                    {
                        AutoIPClient.smAUTOIPState = SM_AUTOIP_SETUP_MESSAGE;
                    }
                }
                else
                {
                    AutoIPClient.flags.bits.checkAddress = false;
                }
    
                break;
    
            // Set up an ARP packet
            case SM_AUTOIP_SETUP_MESSAGE:
    
                AutoIPClient.flags.bits.checkAddress = false;
    
                // Set the bConfigureAutoIP flag- This flag will cause an AutoIP conflict
                // if a response packet is received from the address we're trying to claim.
                AutoIPClient.flags.bits.bConfigureAutoIP = true;
    
                // Configure the fields for a gratuitous ARP packet
            	AutoIPClient.packet.Operation            = ARP_OPERATION_REQ;
            
            	AutoIPClient.packet.TargetMACAddr.v[0]   = 0xff;
            	AutoIPClient.packet.TargetMACAddr.v[1]   = 0xff;
            	AutoIPClient.packet.TargetMACAddr.v[2]   = 0xff;
            	AutoIPClient.packet.TargetMACAddr.v[3]   = 0xff;
            	AutoIPClient.packet.TargetMACAddr.v[4]   = 0xff;
            	AutoIPClient.packet.TargetMACAddr.v[5]   = 0xff;
    
                pConfig->MyIPAddr = AutoIPClient.packet.TargetIPAddr;
                pConfig->MyMask.Val = 0x0000FFFF;
            	memcpy(&AutoIPClient.packet.SenderMACAddr, (void*)&pConfig->MyMACAddr, sizeof(AutoIPClient.packet.SenderMACAddr));
                AutoIPClient.packet.HardwareType  = HW_ETHERNET;
                AutoIPClient.packet.Protocol      = ARP_IP;
                AutoIPClient.packet.MACAddrLen    = sizeof(MAC_ADDR);
                AutoIPClient.packet.ProtocolLen   = sizeof(IP_ADDR);
                AutoIPClient.packet.SenderIPAddr.Val  = AutoIPClient.packet.TargetIPAddr.Val;
    
                SwapARPPacket(&AutoIPClient.packet);
    
                // Generate a random delay between 0 and 1 second
                AutoIPClient.randomDelay = ((LFSRRand() % 20) * SYS_TICK_TicksPerSecondGet()) / 20;
                // Store the current time
                AutoIPClient.eventTime = SYS_TICK_Get();
    
                // Set the state to send the ARP packet
                AutoIPClient.smAUTOIPState = SM_AUTOIP_GRATUITOUS_ARP1;
    
                break;
    
            // Send a gratuitous ARP packet to try and claim our address
            case SM_AUTOIP_GRATUITOUS_ARP1:
            case SM_AUTOIP_GRATUITOUS_ARP2:
            case SM_AUTOIP_GRATUITOUS_ARP3:
                // Check to ensure we've passed the delay time
                if (SYS_TICK_Get() - AutoIPClient.eventTime > AutoIPClient.randomDelay)
                {
                	if(!MACIsTxReady(hMac))
                    {
                        break;
                    }
                    // Store the new event time
                    AutoIPClient.eventTime = SYS_TICK_Get();
                    // Generate a new random delay between 1 and 2 seconds
                    AutoIPClient.randomDelay = SYS_TICK_TicksPerSecondGet() + (((LFSRRand() % 20) * SYS_TICK_TicksPerSecondGet()) / 20);
    
                    // Transmit the packet
                	MACSetWritePtr(hMac, MACGetTxBaseAddr(hMac));
    
                    MACPutHeader(hMac, &AutoIPClient.packet.TargetMACAddr, ETHERTYPE_ARP, sizeof(AutoIPClient.packet));
                    MACPutArray(hMac, (uint8_t*)&AutoIPClient.packet, sizeof(AutoIPClient.packet));
                    MACFlush(hMac);
    
                    // Increment the probe iteration or increment to the delay state
                    AutoIPClient.smAUTOIPState++;
                }
                break;
    
            // Delay for 1-2 seconds after sending the third ARP request before
            // entering the configured state
            case SM_AUTOIP_DELAY:
                if (SYS_TICK_Get() - AutoIPClient.eventTime > AutoIPClient.randomDelay)
                    AutoIPClient.smAUTOIPState = SM_AUTOIP_CONFIGURED;
                break;
    
            // Configure the module to limit the rate at which packets are sent
            case SM_AUTOIP_RATE_LIMIT_SET:
                AutoIPClient.eventTime = SYS_TICK_Get();
                pConfig->MyIPAddr.Val = pConfig->DefaultIPAddr.Val;
                AutoIPClient.smAUTOIPState = SM_AUTOIP_RATE_LIMIT_WAIT;
                break;
    
            // Ensure that we don't try more than one address every 60 seconds
            case SM_AUTOIP_RATE_LIMIT_WAIT:
                if (SYS_TICK_Get() - AutoIPClient.eventTime > SYS_TICK_TicksPerSecondGet() * 60)
                    AutoIPClient.smAUTOIPState = SM_AUTOIP_CHECK_ADDRESS;
                break;
    
            // Configured state
            case SM_AUTOIP_CONFIGURED:
                AutoIPClient.flags.bits.bConfigureAutoIP = false;
                break;
    
            // Address defense state
            case SM_AUTOIP_DEFEND:
                // Prepare and send an ARP response
            	if(!MACIsTxReady(hMac))
                {
                    break;
                }
                AutoIPClient.packet.Operation     = ARP_OPERATION_RESP;
                AutoIPClient.packet.HardwareType  = HW_ETHERNET;
                AutoIPClient.packet.Protocol      = ARP_IP;
    
                SwapARPPacket(&AutoIPClient.packet);
    
            	MACSetWritePtr(hMac, MACGetTxBaseAddr(hMac));
    
                MACPutHeader(hMac, &AutoIPClient.packet.TargetMACAddr, ETHERTYPE_ARP, sizeof(AutoIPClient.packet));
                MACPutArray(hMac, (uint8_t*)&AutoIPClient.packet, sizeof(AutoIPClient.packet));
                MACFlush(hMac);
    
                AutoIPClient.smAUTOIPState = SM_AUTOIP_CONFIGURED;
                break;
        }
    }
}
コード例 #29
0
/*****************************************************************************
  Function:
	void PingDemoTask (void)

  Summary:
	Handles state machine for ping demo processes.
	
  Description:
	This function performs state processing for the ping demo.
	
	This function can be used as a model for applications requiring Ping6 
	capabilities to check if a host is reachable.

  Precondition:
	None.

  Parameters:
	None

  Returns:
  	None
  ***************************************************************************/
void PingDemoTask (void)
{
    switch (pingState)
    {
#if defined (TCPIP_STACK_USE_ICMP_CLIENT)
        case STATE_DNS_SEND_QUERY_IPV4:
            if (!DNSBeginUsage(pNetIf))
                return;

            if (DNSResolve((const char *)targetHostName, DNS_TYPE_A) != DNS_RES_OK)
                return;

            pingTimer = SYS_TICK_Get() + (SYS_TICK_ResolutionGet() * TCPIP_PING_DNS_TIMEOUT);
            pingState = STATE_DNS_GET_RESPONSE_IPV4;
            break;
        case STATE_DNS_GET_RESPONSE_IPV4:
            {
                DNS_RESULT res;
                if ((long)(SYS_TICK_Get() - pingTimer) > 0)
                {
                    SYS_OUT_MESSAGE_LINE("Couldn't resolve", 2);
                    DNSEndUsage(pNetIf);
                    pingState = STATE_IDLE;
                    return;
                } 
    
                res = DNSIsResolved((const char *)targetHostName, &targetAddressIPv4);

                switch (res)
                {
                    case DNS_RES_OK:
                        DNSEndUsage(pNetIf);
                        pingState = STATE_RESOLVE_ARP;
                        break;
                    case DNS_RES_PENDING:
                        
                        break;
                    default:
                        SYS_OUT_MESSAGE_LINE ("Couldn't resolve", 1);
                        DNSEndUsage(pNetIf);
                        pingState = STATE_IDLE;
                        break;
                }
            }
            break;
		case STATE_RESOLVE_ARP:
            if ((targetAddressIPv4.Val & pNetIf->MyMask.Val) == pNetIf->MyMask.Val)
                firstHopAddress.Val = targetAddressIPv4.Val;
            else
                firstHopAddress.Val = pNetIf->MyGateway.Val;
  			ARPResolve(pNetIf, &firstHopAddress);
			pingTimer = SYS_TICK_Get();
			pingState = STATE_ARP_RESOLVED;
			break;

		case STATE_ARP_RESOLVED:
			if(!ARPIsResolved(pNetIf, &firstHopAddress, &targetMACAddr))
			{
				if(SYS_TICK_Get() - pingTimer > (TCPIP_PING_DNS_TIMEOUT * SYS_TICK_TicksPerSecondGet()))
                {
                    SYS_OUT_MESSAGE_LINE ("Couldn't ARP", 1);
					pingState = STATE_IDLE;
                }
				break;
			}

			pingState = STATE_SEND_ECHO_REQUEST_IPV4;
            break;
#endif
#if defined (TCPIP_STACK_USE_IPV6)
        case STATE_DNS_SEND_QUERY_IPV6:
            if (!DNSBeginUsage(pNetIf))
                return;

            if (DNSResolve((const char *)targetHostName, DNS_TYPE_AAAA) != DNS_RES_OK)
                return;

            pingTimer = SYS_TICK_Get() + (SYS_TICK_ResolutionGet() * TCPIP_PING_DNS_TIMEOUT);
            pingState = STATE_DNS_GET_RESPONSE_IPV6;
            break;
        case STATE_DNS_GET_RESPONSE_IPV6:
            {
                DNS_RESULT res;
                if ((long)(SYS_TICK_Get() - pingTimer) > 0)
                {
                    SYS_OUT_MESSAGE_LINE ("Couldn't resolve", 1);
                    DNSEndUsage(pNetIf);
                    pingState = STATE_IDLE;
                    return;
                } 
    
                res = DNSIsResolved((const char *)targetHostName, &targetAddressIPv6);

                switch (res)
                {
                    case DNS_RES_OK:
                        DNSEndUsage(pNetIf);
                        pingState = STATE_SEND_ECHO_REQUEST_IPV6;
                        break;
                    case DNS_RES_PENDING:
                        
                        break;
                    default:
                        SYS_OUT_MESSAGE_LINE ("Couldn't resolve", 1);
                        DNSEndUsage(pNetIf);
                        pingState = STATE_IDLE;
                        break;
                }
            }
            break;
#endif
#if defined(TCPIP_STACK_USE_ICMP_CLIENT)
        case STATE_SEND_ECHO_REQUEST_IPV4:
            {
                NODE_INFO info;

                info.IPAddr = targetAddressIPv4;
                memcpy (&info.MACAddr, &targetMACAddr, sizeof (MAC_ADDR));
                ICMPSendEchoRequest (&info, ++wICMPSequenceNumber, 0xBEEF);

    			// Record the current time.  This will be used as a basis for 
    			// finding the echo response time, which exludes the ARP and DNS 
    			// steps
   			    pingTimer = SYS_TICK_Get();
    
                pingCount++;

                SYS_OUT_MESSAGE_LINE ("Pinging...", 1);

    			// Echo sent, advance state
    			pingState = STATE_GET_RESPONSE_IPV4;
            }
            break;
#endif
#if defined (TCPIP_STACK_USE_IPV6)
        case STATE_SEND_ECHO_REQUEST_IPV6:
            {
                IP_PACKET * pkt;
                IPV6_ADDR_STRUCT * localAddress;

                localAddress = TCPIP_IPV6_DAS_SelectSourceAddress (pNetIf, &targetAddressIPv6, NULL);

                if (localAddress == NULL)
                {
                    SYS_OUT_MESSAGE_LINE ("No local addr!", 1);
                    pingState = STATE_IDLE;
                    break;
                }
    
                pkt = TCPIP_ICMPV6_PutHeaderEchoRequest (pNetIf, &localAddress->address, &targetAddressIPv6, ICMPV6_INFO_ECHO_REQUEST, 
                                                    0xEFBE, ++wICMPSequenceNumber);
    
                if (TCPIP_IP_IsTxPutReady(pkt, 4) < 4)
                {
                    TCPIP_IP_FreePacket (pkt);
                    return;
                }
    
                TCPIP_IP_PutArray (pkt, (uint8_t *)&miscData, sizeof (uint32_t));
    
                // Just let the IPv6 module figure out the next hop neighbor and its MAC address
                TCPIP_ICMPV6_Flush (pkt);
    		
    			// Record the current time.  This will be used as a basis for 
    			// finding the echo response time, which exludes the ARP and DNS 
    			// steps
   			    pingTimer = SYS_TICK_Get();
    
                pingCount++;

                SYS_OUT_MESSAGE_LINE ("Pinging...", 1);

    			// Echo sent, advance state
    			pingState = STATE_GET_RESPONSE_IPV6;
            }
            break;
#endif
#if defined (TCPIP_STACK_USE_ICMP_CLIENT)
        case STATE_GET_RESPONSE_IPV4:
            if ((long)(SYS_TICK_Get() - pingTimer) > (SYS_TICK_ResolutionGet() * TCPIP_PING_TIMEOUT))
            {
                SYS_OUT_MESSAGE_LINE("Ping timeout", 1);
                pingState = STATE_IDLE;
            }            
            break;
#endif
#if defined (TCPIP_STACK_USE_IPV6)
        case STATE_GET_RESPONSE_IPV6:
            if ((long)(SYS_TICK_Get() - pingTimer) > (SYS_TICK_ResolutionGet() * TCPIP_PING_TIMEOUT))
            {
                SYS_OUT_MESSAGE_LINE ("Ping timeout", 1);
                pingState = STATE_IDLE;
            }
            break;
#endif
        default:
        case STATE_IDLE:
            break;
        
    }
}