⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sys_arch.c

📁 最新的lwip 1.3.0版本在ucos平台上的移植
💻 C
字号:
/*
 * Copyright (c) 2001, Swedish Institute of Computer Science.
 * All rights reserved. 
 *
 * Redistribution and use in source and binary forms, with or without 
 * modification, are permitted provided that the following conditions 
 * are met: 
 * 1. Redistributions of source code must retain the above copyright 
 *    notice, this list of conditions and the following disclaimer. 
 * 2. Redistributions in binary form must reproduce the above copyright 
 *    notice, this list of conditions and the following disclaimer in the 
 *    documentation and/or other materials provided with the distribution. 
 * 3. Neither the name of the Institute nor the names of its contributors 
 *    may be used to endorse or promote products derived from this software 
 *    without specific prior written permission. 
 *
 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
 * SUCH DAMAGE. 
 *
 * This file is part of the lwIP TCP/IP stack.
 * 
 * Author: Adam Dunkels <adam@sics.se>
 *
 * $Id: sys_arch.c,v 1.1.1.1 2003/05/17 05:06:56 chenyu Exp $
 */

#include "lwip/debug.h"

#include "lwip/def.h"
#include "lwip/sys.h"
#include "lwip/mem.h"
#include "lwip/sio.h"

//yangye 2003-1-22
#include "sys_arch.h" 
//yangye 2003-1-27
//notice: we use OSTaskQuery in sys_arch_timeouts() !
//#include "ucos_ii.h"
//#include "os_cfg.h"

//extern INT8U  OSQFlush (OS_EVENT *pevent);
//extern OS_EVENT  *OSQDel (OS_EVENT *pevent, INT8U opt, INT8U *err);
//extern INT8U  OSTaskQuery (INT8U prio, OS_TCB *pdata);

#include <sal_os.h>
#include <ssi/trace.h>

const void * const pvNullPointer;

static OS_MEM *pQueueMem;

static char pcQueueMemoryPool[MAX_QUEUES * sizeof(TQ_DESCR) ];

//yangye 2003-1-27
struct sys_timeouts lwip_timeouts[OS_LOWEST_PRIO+1];
struct sys_timeouts null_timeouts;

OS_STK LWIP_TASK_STK[LWIP_TASK_MAX_DEF][LWIP_STK_SIZE];
u8_t curr_prio_offset;

/*-----------------------------------------------------------------------------------*/
sys_mbox_t sys_mbox_new(int size)
{
    u8_t       ucErr;
    PQ_DESCR    pQDesc;
    
    pQDesc = OSMemGet( pQueueMem, &ucErr );
    if( ucErr == OS_NO_ERR ) {   
        pQDesc->pQ = OSQCreate( &(pQDesc->pvQEntries[0]), MAX_QUEUE_ENTRIES );       
        if( pQDesc->pQ != NULL ) {
            return pQDesc;
        }
    } 
    return SYS_MBOX_NULL;
}

/*-----------------------------------------------------------------------------------*/
void
sys_mbox_free(sys_mbox_t mbox)
{
    u8_t     ucErr;
    
    //clear OSQ EVENT
    OSQFlush( mbox->pQ );
    //del OSQ EVENT
    (void)OSQDel( mbox->pQ, OS_DEL_NO_PEND, &ucErr);
    //put mem back to mem queue
    ucErr = OSMemPut( pQueueMem, mbox );
}

/*-----------------------------------------------------------------------------------*/
void
sys_mbox_post(sys_mbox_t mbox, void *data)
{
    if( !data ) 
	    data = (void*)&pvNullPointer;
    if (OSQPost( mbox->pQ, data) != OS_NO_ERR)
    {
        func_trace(TRC_ERR, "mbox post error");
    }
}

err_t sys_mbox_trypost(sys_mbox_t mbox, void *data)
{
    if( !data ) 
	    data = (void*)&pvNullPointer;
    if (OSQPost( mbox->pQ, data) != OS_NO_ERR)
    {
        return ERR_MEM;
    }
    else
    {
        return ERR_OK;
    }
}

/*-----------------------------------------------------------------------------------*/
u32_t
sys_arch_mbox_fetch(sys_mbox_t mbox, void **data, u32_t timeout)
{
    u8_t     ucErr;
    u16_t ucos_timeout;
  //yangye 2003-1-27
  //in lwip ,timeout is  millisecond 
  //in ucosII ,timeout is timer  tick! 
  //chang timeout from millisecond to ucos tick
  ucos_timeout = 0;
  if(timeout != 0){
  ucos_timeout = (timeout * OS_TICKS_PER_SEC)/1000;
  if(ucos_timeout < 1)
  	ucos_timeout = 1;
  else if(ucos_timeout > 65535)
  	ucos_timeout = 65535;
  }  
    
  //yangye 2003-1-29
  //it is very importent!!!! 
  //sometimes lwip calls sys_mbox_fetch(mbox,NULL)
  //it is dangrous to return (void *) to NULL ! (from OSQPend())
  if(data != NULL){
    *data = OSQPend( mbox->pQ, (u16_t)ucos_timeout, &ucErr );        
  }else{
    //just discard return value if data==NULL
    OSQPend(mbox->pQ,(u16_t)ucos_timeout,&ucErr);
  }
    
  if( ucErr == OS_TIMEOUT ) {
        timeout = SYS_ARCH_TIMEOUT;
    } else {
      if(*data == (void*)&pvNullPointer ) 
	  *data = NULL;
      timeout = 1;
    }
  return timeout;
}

u32_t sys_arch_mbox_tryfetch(sys_mbox_t mbox, void **data)
{
    u8_t     ucErr;

    if(data != NULL)
    {
      *data = OSQAccept(mbox->pQ, &ucErr );        
    }else
    {
      //just discard return value if data==NULL
      OSQAccept(mbox->pQ, &ucErr ); 
    }

    if (ucErr == OS_Q_EMPTY)
    {
        return SYS_MBOX_EMPTY;
    }
    else if (ucErr == OS_NO_ERR)
    {
        return 0;
    }
    else
    {
        func_trace(TRC_ERR, "try fetch error");
        return SYS_MBOX_EMPTY;
    }
}

/*-----------------------------------------------------------------------------------*/

sys_sem_t sys_sem_new(u8_t count)
{
    sys_sem_t pSem;
    pSem = OSSemCreate((u16_t)count );
    return pSem;
}

/*-----------------------------------------------------------------------------------*/

void sys_sem_signal(sys_sem_t sem)
{
    u8_t     ucErr;
    ucErr = OSSemPost((OS_EVENT *)sem );
}

/*-----------------------------------------------------------------------------------*/
//yangye 2003-1-25
u32_t sys_arch_sem_wait(sys_sem_t sem, u32_t timeout)
{
  u8_t err;
  u32_t ucos_timeout;
  //yangye 2003-1-27
  //in lwip ,timeout is  millisecond 
  //in ucosII ,timeout is timer  tick! 
  //chang timeout from millisecond to ucos tick
  ucos_timeout = 0;
  if(timeout != 0){
  ucos_timeout = (timeout * OS_TICKS_PER_SEC)/1000;
  if(ucos_timeout < 1)
  	ucos_timeout = 1;
  else if(ucos_timeout > 65535)
  	ucos_timeout = 65535;
  }
  	
  OSSemPend ((OS_EVENT *)sem,(u16_t)ucos_timeout, (u8_t *)&err);
  //should not return 0 when wait time is 0, only when timeout!
  //see sys_arch.txt in lwip/doc 
  if(err == OS_TIMEOUT)
  	return SYS_ARCH_TIMEOUT;
  else
  	return 1;
}

/*-----------------------------------------------------------------------------------*/

void sys_sem_free(sys_sem_t sem)
{
    u8_t     ucErr;
    (void)OSSemDel((OS_EVENT *)sem, OS_DEL_NO_PEND, &ucErr );
}

/*-----------------------------------------------------------------------------------*/
void sys_init(void)
{
	u8_t i;
	//this func is called first in lwip task!
	u8_t   ucErr;
	//init mem used by sys_mbox_t
	//use ucosII functions
	pQueueMem = OSMemCreate( (void*)pcQueueMemoryPool, MAX_QUEUES, sizeof(TQ_DESCR), &ucErr );
	//init lwip task prio offset
	curr_prio_offset = 0;

	#if 0
	//init lwip_timeouts for every lwip task
	for(i=0;i<LWIP_TASK_MAX_DEF;i++)
	{
		lwip_timeouts[i].next = NULL;
	}
	#endif

    for(i=0;i<OS_LOWEST_PRIO+1;i++)
	{
		lwip_timeouts[i].next = NULL;
	}
}
/*-----------------------------------------------------------------------------------*/

/*----------------------------------------------------------------------*/
struct sys_timeouts * sys_arch_timeouts(void)
{
	u8_t curr_prio;
	s16_t err,offset;

	OS_TCB curr_task_pcb;

	null_timeouts.next = NULL;
	//get current task prio
	err = OSTaskQuery(OS_PRIO_SELF,&curr_task_pcb);
	curr_prio = curr_task_pcb.OSTCBPrio;

    #if 0
	offset = curr_prio - LWIP_TASK_START_PRIO;
	//not called by a lwip task ,return timeouts->NULL
	if(offset < 0 || offset >= LWIP_TASK_MAX_DEF)
	{
		return &null_timeouts;
	}
	return &lwip_timeouts[offset];
	#endif
    return &lwip_timeouts[curr_prio];

}
/*------------------------------------------------------------------------*/



sys_thread_t
sys_thread_new(char *name, void (* function)(void *arg), void *arg, int stacksize, int prio)
{
	if(curr_prio_offset < LWIP_TASK_MAX_DEF)
  	{
  		OSTaskCreate(function, (void *)0x1111, &LWIP_TASK_STK[curr_prio_offset][LWIP_STK_SIZE-1],LWIP_TASK_START_PRIO+curr_prio_offset );
 		curr_prio_offset++; 
 		return 0;
  	} 
  	else 
  	{
    	func_trace(TRC_ERR, "lwip task prio out of range ! error! ");
    	return 1;
  	}
}


sio_fd_t sio_open(u8_t s)
{
    func_trace(TRC_ERR, "sio_open not implemented!");
    return NULL;
}

void sio_send(u8_t s, sio_fd_t fd)
{

    func_trace(TRC_ERR, "sio_send not implemented!");
}

u8_t sio_recv(sio_fd_t fd)
{
    func_trace(TRC_ERR, "sio_recv not implemented!");
    return 0;
}



⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -