fix network driver:add select,ioctl;expand TCP packet length
parent
e5fbb28a9d
commit
863d783ea0
|
@ -292,6 +292,7 @@ double k_spi_driver::set_clock_rate(k_spi_device_driver &device, double clock_ra
|
|||
int k_spi_driver::read(k_spi_device_driver &device, gsl::span<uint8_t> buffer)
|
||||
{
|
||||
COMMON_ENTRY;
|
||||
|
||||
setup_device(device);
|
||||
|
||||
uint32_t i = 0;
|
||||
|
@ -308,6 +309,7 @@ int k_spi_driver::read(k_spi_device_driver &device, gsl::span<uint8_t> buffer)
|
|||
|
||||
if (rx_frames < SPI_TRANSMISSION_THRESHOLD)
|
||||
{
|
||||
vTaskEnterCritical();
|
||||
size_t index, fifo_len;
|
||||
while (rx_frames)
|
||||
{
|
||||
|
@ -335,6 +337,7 @@ int k_spi_driver::read(k_spi_device_driver &device, gsl::span<uint8_t> buffer)
|
|||
}
|
||||
rx_frames -= fifo_len;
|
||||
}
|
||||
vTaskExitCritical();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -355,12 +358,14 @@ int k_spi_driver::read(k_spi_device_driver &device, gsl::span<uint8_t> buffer)
|
|||
spi_.ser = 0x00;
|
||||
spi_.ssienr = 0x00;
|
||||
spi_.dmacr = 0x00;
|
||||
|
||||
return buffer.size();
|
||||
}
|
||||
|
||||
int k_spi_driver::write(k_spi_device_driver &device, gsl::span<const uint8_t> buffer)
|
||||
{
|
||||
COMMON_ENTRY;
|
||||
|
||||
setup_device(device);
|
||||
|
||||
uint32_t i = 0;
|
||||
|
@ -371,6 +376,7 @@ int k_spi_driver::write(k_spi_device_driver &device, gsl::span<const uint8_t> bu
|
|||
|
||||
if (tx_frames < SPI_TRANSMISSION_THRESHOLD)
|
||||
{
|
||||
vTaskEnterCritical();
|
||||
size_t index, fifo_len;
|
||||
spi_.ssienr = 0x01;
|
||||
write_inst_addr(spi_.dr, &buffer_write, device.inst_width_);
|
||||
|
@ -399,6 +405,7 @@ int k_spi_driver::write(k_spi_device_driver &device, gsl::span<const uint8_t> bu
|
|||
}
|
||||
tx_buffer_len -= fifo_len;
|
||||
}
|
||||
vTaskExitCritical();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -420,6 +427,7 @@ int k_spi_driver::write(k_spi_device_driver &device, gsl::span<const uint8_t> bu
|
|||
spi_.ser = 0x00;
|
||||
spi_.ssienr = 0x00;
|
||||
spi_.dmacr = 0x00;
|
||||
|
||||
return buffer.size();
|
||||
}
|
||||
|
||||
|
@ -452,6 +460,7 @@ int k_spi_driver::read_write(k_spi_device_driver &device, gsl::span<const uint8_
|
|||
|
||||
if (rx_frames < SPI_TRANSMISSION_THRESHOLD)
|
||||
{
|
||||
vTaskEnterCritical();
|
||||
size_t index, fifo_len;
|
||||
spi_.ctrlr1 = rx_frames - 1;
|
||||
spi_.ssienr = 0x01;
|
||||
|
@ -504,6 +513,7 @@ int k_spi_driver::read_write(k_spi_device_driver &device, gsl::span<const uint8_
|
|||
spi_.ser = device.chip_select_mask_;
|
||||
rx_buffer_len -= fifo_len;
|
||||
}
|
||||
vTaskExitCritical();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
|
@ -348,8 +348,9 @@ public:
|
|||
{
|
||||
configASSERT(length <= std::numeric_limits<uint16_t>::max());
|
||||
while (read(DM9051_TCR) & DM9051_TCR_SET)
|
||||
;
|
||||
|
||||
{
|
||||
usleep(5000);
|
||||
}
|
||||
write(DM9051_TXPLL, length & 0xff);
|
||||
write(DM9051_TXPLH, (length >> 8) & 0xff);
|
||||
}
|
||||
|
@ -455,14 +456,14 @@ private:
|
|||
xSemaphoreGiveFromISR(driver.interrupt_event_, &xHigherPriorityTaskWoken);
|
||||
if (xHigherPriorityTaskWoken)
|
||||
{
|
||||
portYIELD();
|
||||
portYIELD_FROM_ISR();
|
||||
}
|
||||
}
|
||||
|
||||
uint8_t read(uint8_t addr)
|
||||
{
|
||||
const uint8_t to_write[1] = { addr };
|
||||
uint8_t to_read[1];
|
||||
uint8_t to_read[1] = { 0 };
|
||||
spi_dev_->transfer_sequential({ to_write }, { to_read });
|
||||
return to_read[0];
|
||||
}
|
||||
|
|
|
@ -68,7 +68,7 @@
|
|||
#define configUSE_PORT_OPTIMISED_TASK_SELECTION 0
|
||||
#define configMAX_PRIORITIES ( 5 )
|
||||
#define configMAX_TASK_NAME_LEN ( 16 )
|
||||
#define configUSE_TRACE_FACILITY 0
|
||||
#define configUSE_TRACE_FACILITY 1
|
||||
#define configUSE_16_BIT_TICKS 0
|
||||
#define configIDLE_SHOULD_YIELD 0
|
||||
#define configQUEUE_REGISTRY_SIZE 8
|
||||
|
|
|
@ -54,12 +54,15 @@ void handle_irq_m_soft(uintptr_t *regs, uintptr_t cause)
|
|||
|
||||
void core_sync_request(uint64_t core_id, int event)
|
||||
{
|
||||
vTaskEnterCritical();
|
||||
|
||||
corelock_lock(&s_core_sync_locks[core_id]);
|
||||
while (s_core_sync_events[core_id] != CORE_SYNC_NONE)
|
||||
;
|
||||
s_core_sync_events[core_id] = event;
|
||||
clint_ipi_send(core_id);
|
||||
corelock_unlock(&s_core_sync_locks[core_id]);
|
||||
vTaskExitCritical();
|
||||
}
|
||||
|
||||
void core_sync_complete(uint64_t core_id)
|
||||
|
|
|
@ -60,6 +60,23 @@ MAKE_ENUM_CLASS_BITMASK_TYPE(file_access_t);
|
|||
MAKE_ENUM_CLASS_BITMASK_TYPE(file_mode_t);
|
||||
MAKE_ENUM_CLASS_BITMASK_TYPE(socket_message_flag_t);
|
||||
|
||||
class errno_exception : public std::runtime_error
|
||||
{
|
||||
public:
|
||||
explicit errno_exception(const char *msg, int code) noexcept
|
||||
: runtime_error(msg), code_(code)
|
||||
{
|
||||
}
|
||||
|
||||
int code() const noexcept
|
||||
{
|
||||
return code_;
|
||||
}
|
||||
|
||||
private:
|
||||
int code_;
|
||||
};
|
||||
|
||||
class object_access : public virtual object
|
||||
{
|
||||
public:
|
||||
|
@ -410,7 +427,7 @@ public:
|
|||
virtual void end_receive() = 0;
|
||||
};
|
||||
|
||||
class network_socket : public virtual object_access
|
||||
class network_socket : public virtual custom_driver, public virtual object_access
|
||||
{
|
||||
public:
|
||||
virtual object_accessor<network_socket> accept(socket_address_t *remote_address) = 0;
|
||||
|
@ -424,6 +441,8 @@ public:
|
|||
virtual size_t receive_from(gsl::span<uint8_t> buffer, socket_message_flag_t flags, socket_address_t *from) = 0;
|
||||
virtual size_t read(gsl::span<uint8_t> buffer) = 0;
|
||||
virtual size_t write(gsl::span<const uint8_t> buffer) = 0;
|
||||
virtual int fcntl(int cmd, int val) = 0;
|
||||
virtual void select(fd_set *readset, fd_set *writeset, fd_set *exceptset, struct timeval *timeout) = 0;
|
||||
};
|
||||
|
||||
extern driver_registry_t g_hal_drivers[];
|
||||
|
|
|
@ -257,6 +257,8 @@ int network_socket_send_to(handle_t socket_handle, const uint8_t *data, size_t l
|
|||
* - other Fail
|
||||
*/
|
||||
int network_socket_receive_from(handle_t socket_handle, uint8_t *data, size_t len, socket_message_flag_t flags, socket_address_t *from);
|
||||
int network_socket_fcntl(handle_t socket_handle, int cmd, int val);
|
||||
int network_socket_select(handle_t socket_handle, fd_set *readset, fd_set *writeset, fd_set *exceptset, struct timeval *timeout);
|
||||
|
||||
/**
|
||||
* @brief Get host address information by name
|
||||
|
|
|
@ -335,6 +335,19 @@ typedef enum _dhcp_state
|
|||
DHCP_FAIL
|
||||
} dhcp_state_t;
|
||||
|
||||
#define SYS_IOCPARM_MASK 0x7fU /* parameters must be < 128 bytes */
|
||||
#define SYS_IOC_VOID 0x20000000UL /* no parameters */
|
||||
#define SYS_IOC_OUT 0x40000000UL /* copy out parameters */
|
||||
#define SYS_IOC_IN 0x80000000UL /* copy in parameters */
|
||||
#define SYS_IOC_INOUT (SYS_IOC_IN | SYS_IOC_OUT) /* 0x20000000 distinguishes new & old ioctl's */
|
||||
#define SYS_IO(x, y) (SYS_IOC_VOID | ((x) << 8) | (y))
|
||||
|
||||
#define SYS_IOR(x, y, t) (SYS_IOC_OUT | (((uint32_t)sizeof(t) & SYS_IOCPARM_MASK) << 16) | ((x) << 8) | (y))
|
||||
|
||||
#define SYS_IOW(x, y, t) (SYS_IOC_IN | (((uint32_t)sizeof(t) & SYS_IOCPARM_MASK) << 16) | ((x) << 8) | (y))
|
||||
|
||||
#define SYS_FIONBIO SYS_IOW('f', 126, uint32_t) /* set/clear non-blocking i/o */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -45,6 +45,13 @@ using namespace sys;
|
|||
} \
|
||||
}
|
||||
|
||||
#define CATCH_ALL \
|
||||
catch (errno_exception & e) \
|
||||
{ \
|
||||
errno = e.code(); \
|
||||
return -1; \
|
||||
}
|
||||
|
||||
typedef struct
|
||||
{
|
||||
object_accessor<object_access> object;
|
||||
|
@ -192,6 +199,8 @@ static void dma_add_free();
|
|||
|
||||
int io_read(handle_t file, uint8_t *buffer, size_t len)
|
||||
{
|
||||
try
|
||||
{
|
||||
configASSERT(file >= HANDLE_OFFSET);
|
||||
_file *rfile = (_file *)handles_[file - HANDLE_OFFSET];
|
||||
/* clang-format off */
|
||||
|
@ -205,6 +214,8 @@ int io_read(handle_t file, uint8_t *buffer, size_t len)
|
|||
return -1;
|
||||
}
|
||||
/* clang-format on */
|
||||
}
|
||||
CATCH_ALL;
|
||||
}
|
||||
|
||||
static void io_free(_file *file)
|
||||
|
@ -273,6 +284,8 @@ int io_close(handle_t file)
|
|||
|
||||
int io_write(handle_t file, const uint8_t *buffer, size_t len)
|
||||
{
|
||||
try
|
||||
{
|
||||
configASSERT(file >= HANDLE_OFFSET);
|
||||
_file *rfile = (_file *)handles_[file - HANDLE_OFFSET];
|
||||
/* clang-format off */
|
||||
|
@ -286,14 +299,24 @@ int io_write(handle_t file, const uint8_t *buffer, size_t len)
|
|||
return -1;
|
||||
}
|
||||
/* clang-format on */
|
||||
}
|
||||
CATCH_ALL;
|
||||
}
|
||||
|
||||
int io_control(handle_t file, uint32_t control_code, const uint8_t *write_buffer, size_t write_len, uint8_t *read_buffer, size_t read_len)
|
||||
{
|
||||
try
|
||||
{
|
||||
configASSERT(file >= HANDLE_OFFSET);
|
||||
_file *rfile = (_file *)handles_[file - HANDLE_OFFSET];
|
||||
DEFINE_CONTROL_PROXY(custom)
|
||||
|
||||
else
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
CATCH_ALL;
|
||||
|
||||
}
|
||||
|
||||
/* Device IO Implementation Helper Macros */
|
||||
|
|
|
@ -13,6 +13,7 @@
|
|||
* limitations under the License.
|
||||
*/
|
||||
#include "network.h"
|
||||
#include "semphr.h"
|
||||
#include "FreeRTOS.h"
|
||||
#include "devices.h"
|
||||
#include "kernel/driver_impl.hpp"
|
||||
|
@ -26,9 +27,11 @@
|
|||
#include <lwip/netdb.h>
|
||||
#include <netif/ethernet.h>
|
||||
#include <string.h>
|
||||
|
||||
using namespace sys;
|
||||
|
||||
#define MAX_DHCP_TRIES 5
|
||||
#define NETIF_GUARD_BLOCK_TIME (250 )
|
||||
|
||||
int network_init()
|
||||
{
|
||||
|
@ -43,7 +46,7 @@ public:
|
|||
: adapter_(std::move(adapter))
|
||||
{
|
||||
ip4_addr_t ipaddr, netmask, gw;
|
||||
completion_event_ = xSemaphoreCreateCounting(20, 0);
|
||||
completion_event_ = xSemaphoreCreateBinary();
|
||||
|
||||
IP4_ADDR(&ipaddr, ip_address.data[0], ip_address.data[1], ip_address.data[2], ip_address.data[3]);
|
||||
IP4_ADDR(&netmask, net_mask.data[0], net_mask.data[1], net_mask.data[2], net_mask.data[3]);
|
||||
|
@ -60,7 +63,7 @@ public:
|
|||
netif_set_up(&netif_);
|
||||
|
||||
TaskHandle_t h;
|
||||
auto ret = xTaskCreate(poll_thread, "poll", 10240, this, 3, &h);
|
||||
auto ret = xTaskCreate(poll_thread, "poll", 4096*8, this, 3, &h);
|
||||
configASSERT(ret == pdTRUE);
|
||||
}
|
||||
else
|
||||
|
@ -206,7 +209,7 @@ private:
|
|||
|
||||
static void ethernetif_input(struct netif *netif)
|
||||
{
|
||||
struct pbuf *p;
|
||||
struct pbuf *p = NULL;
|
||||
|
||||
/* move received packet into a new pbuf */
|
||||
p = low_level_input(netif);
|
||||
|
@ -267,17 +270,24 @@ private:
|
|||
|
||||
static struct pbuf *low_level_input(struct netif *netif)
|
||||
{
|
||||
static xSemaphoreHandle xRxSemaphore = NULL;
|
||||
auto ðnetif = *reinterpret_cast<k_ethernet_interface *>(netif->state);
|
||||
auto &adapter = ethnetif.adapter_;
|
||||
struct pbuf *p, *q;
|
||||
struct pbuf *p = NULL, *q = NULL;
|
||||
u16_t len;
|
||||
if (xRxSemaphore == NULL)
|
||||
{
|
||||
vSemaphoreCreateBinary (xRxSemaphore);
|
||||
}
|
||||
|
||||
if (xSemaphoreTake(xRxSemaphore, NETIF_GUARD_BLOCK_TIME))
|
||||
{
|
||||
/* Obtain the size of the packet and put it into the "len" variable. */
|
||||
len = adapter->begin_receive();
|
||||
|
||||
#if ETH_PAD_SIZE
|
||||
#if ETH_PAD_SIZE
|
||||
len += ETH_PAD_SIZE; /* allow room for Ethernet padding */
|
||||
#endif
|
||||
#endif
|
||||
|
||||
/* We allocate a pbuf chain of pbufs from the pool. */
|
||||
p = pbuf_alloc(PBUF_RAW, len, PBUF_POOL);
|
||||
|
@ -285,9 +295,9 @@ private:
|
|||
if (p != NULL)
|
||||
{
|
||||
|
||||
#if ETH_PAD_SIZE
|
||||
#if ETH_PAD_SIZE
|
||||
pbuf_remove_header(p, ETH_PAD_SIZE); /* drop the padding word */
|
||||
#endif
|
||||
#endif
|
||||
|
||||
/* We iterate over the pbuf chain until we have read the entire
|
||||
* packet into the pbuf. */
|
||||
|
@ -317,9 +327,9 @@ private:
|
|||
/* unicast packet*/
|
||||
MIB2_STATS_NETIF_INC(netif, ifinucastpkts);
|
||||
}
|
||||
#if ETH_PAD_SIZE
|
||||
#if ETH_PAD_SIZE
|
||||
pbuf_add_header(p, ETH_PAD_SIZE); /* reclaim the padding word */
|
||||
#endif
|
||||
#endif
|
||||
|
||||
LINK_STATS_INC(link.recv);
|
||||
}
|
||||
|
@ -331,21 +341,32 @@ private:
|
|||
LINK_STATS_INC(link.drop);
|
||||
MIB2_STATS_NETIF_INC(netif, ifindiscards);
|
||||
}
|
||||
|
||||
xSemaphoreGive(xRxSemaphore);
|
||||
}
|
||||
return p;
|
||||
}
|
||||
|
||||
static err_t low_level_output(struct netif *netif, struct pbuf *p)
|
||||
{
|
||||
static xSemaphoreHandle xTxSemaphore = NULL;
|
||||
auto ðnetif = *reinterpret_cast<k_ethernet_interface *>(netif->state);
|
||||
auto &adapter = ethnetif.adapter_;
|
||||
struct pbuf *q;
|
||||
|
||||
if (xTxSemaphore == NULL)
|
||||
{
|
||||
xTxSemaphore = xSemaphoreCreateMutex();
|
||||
}
|
||||
|
||||
if (xTxSemaphore != NULL)
|
||||
{
|
||||
if (xSemaphoreTake(xTxSemaphore, NETIF_GUARD_BLOCK_TIME))
|
||||
{
|
||||
adapter->begin_send(p->tot_len);
|
||||
|
||||
#if ETH_PAD_SIZE
|
||||
#if ETH_PAD_SIZE
|
||||
pbuf_remove_header(p, ETH_PAD_SIZE); /* drop the padding word */
|
||||
#endif
|
||||
#endif
|
||||
|
||||
for (q = p; q != NULL; q = q->next)
|
||||
{
|
||||
|
@ -370,12 +391,14 @@ private:
|
|||
}
|
||||
/* increase ifoutdiscards or ifouterrors on error */
|
||||
|
||||
#if ETH_PAD_SIZE
|
||||
#if ETH_PAD_SIZE
|
||||
pbuf_add_header(p, ETH_PAD_SIZE); /* reclaim the padding word */
|
||||
#endif
|
||||
#endif
|
||||
|
||||
LINK_STATS_INC(link.xmit);
|
||||
|
||||
xSemaphoreGive(xTxSemaphore);
|
||||
}
|
||||
}
|
||||
return ERR_OK;
|
||||
}
|
||||
|
||||
|
|
|
@ -17,6 +17,7 @@
|
|||
#include "kernel/driver_impl.hpp"
|
||||
#include "network.h"
|
||||
#include <lwip/sockets.h>
|
||||
#include <lwip/errno.h>
|
||||
#include <string.h>
|
||||
|
||||
using namespace sys;
|
||||
|
@ -24,7 +25,9 @@ using namespace sys;
|
|||
static void check_lwip_error(int result)
|
||||
{
|
||||
if (result < 0)
|
||||
throw std::runtime_error(strerror(errno));
|
||||
{
|
||||
throw errno_exception(strerror(errno), errno);
|
||||
}
|
||||
}
|
||||
|
||||
static void to_lwip_sockaddr(sockaddr_in &addr, const socket_address_t &socket_addr)
|
||||
|
@ -104,6 +107,10 @@ public:
|
|||
lwip_close(sock_);
|
||||
}
|
||||
|
||||
virtual void install() override
|
||||
{
|
||||
}
|
||||
|
||||
virtual object_accessor<network_socket> accept(socket_address_t *remote_address) override
|
||||
{
|
||||
object_ptr<k_network_socket> socket(std::in_place, new k_network_socket());
|
||||
|
@ -260,6 +267,25 @@ public:
|
|||
return ret;
|
||||
}
|
||||
|
||||
virtual int fcntl(int cmd, int val) override
|
||||
{
|
||||
auto ret = lwip_fcntl(sock_, cmd, val);
|
||||
check_lwip_error(ret);
|
||||
return ret;
|
||||
}
|
||||
|
||||
virtual void select(fd_set *readset, fd_set *writeset, fd_set *exceptset, struct timeval *timeout) override
|
||||
{
|
||||
check_lwip_error(lwip_select(sock_ + 1, readset, writeset, exceptset, timeout));
|
||||
}
|
||||
|
||||
virtual int control(uint32_t control_code, gsl::span<const uint8_t> write_buffer, gsl::span<uint8_t> read_buffer) override
|
||||
{
|
||||
int val = *reinterpret_cast<const int *>(write_buffer.data());
|
||||
check_lwip_error(lwip_ioctl(sock_, (unsigned int)control_code, &val));
|
||||
return 0;
|
||||
}
|
||||
|
||||
private:
|
||||
k_network_socket()
|
||||
: sock_(0)
|
||||
|
@ -276,7 +302,11 @@ private:
|
|||
auto f = obj.as<k_network_socket>();
|
||||
|
||||
#define CATCH_ALL \
|
||||
catch (...) { return -1; }
|
||||
catch (errno_exception &e) \
|
||||
{ \
|
||||
errno = e.code(); \
|
||||
return -1; \
|
||||
}
|
||||
|
||||
#define CHECK_ARG(x) \
|
||||
if (!x) \
|
||||
|
@ -411,6 +441,29 @@ int network_socket_receive_from(handle_t socket_handle, uint8_t *data, size_t le
|
|||
CATCH_ALL;
|
||||
}
|
||||
|
||||
int network_socket_fcntl(handle_t socket_handle, int cmd, int val)
|
||||
{
|
||||
try
|
||||
{
|
||||
SOCKET_ENTRY;
|
||||
|
||||
return f->fcntl(cmd, val);
|
||||
}
|
||||
CATCH_ALL;
|
||||
}
|
||||
|
||||
int network_socket_select(int socket_handle, fd_set *readset, fd_set *writeset, fd_set *exceptset, struct timeval *timeout)
|
||||
{
|
||||
try
|
||||
{
|
||||
SOCKET_ENTRY;
|
||||
|
||||
f->select(readset, writeset, exceptset, timeout);
|
||||
return 0;
|
||||
}
|
||||
CATCH_ALL;
|
||||
}
|
||||
|
||||
int network_socket_addr_parse(const char *ip_addr, int port, uint8_t *socket_addr)
|
||||
{
|
||||
try
|
||||
|
|
|
@ -202,9 +202,9 @@ configIDLE_TASK_NAME in FreeRTOSConfig.h. */
|
|||
UBaseType_t uxTopPriority; \
|
||||
\
|
||||
/* Find the highest priority list that contains ready tasks. */ \
|
||||
portGET_HIGHEST_PRIORITY( uxTopPriority, uxTopReadyPriority ); \
|
||||
configASSERT( listCURRENT_LIST_LENGTH( &( pxReadyTasksLists[ uxTopPriority ] ) ) > 0 ); \
|
||||
listGET_OWNER_OF_NEXT_ENTRY( pxCurrentTCB, &( pxReadyTasksLists[ uxTopPriority ] ) ); \
|
||||
portGET_HIGHEST_PRIORITY( uxTopPriority, uxTopReadyPriority[uxPsrId] ); \
|
||||
configASSERT( listCURRENT_LIST_LENGTH( &( pxReadyTasksLists[uxPsrId][ uxTopPriority ] ) ) > 0 ); \
|
||||
listGET_OWNER_OF_NEXT_ENTRY( pxCurrentTCB[uxPsrId], &( pxReadyTasksLists[uxPsrId][ uxTopPriority ] ) ); \
|
||||
} /* taskSELECT_HIGHEST_PRIORITY_TASK() */
|
||||
|
||||
/*-----------------------------------------------------------*/
|
||||
|
@ -214,9 +214,9 @@ configIDLE_TASK_NAME in FreeRTOSConfig.h. */
|
|||
or suspended list then it won't be in a ready list. */
|
||||
#define taskRESET_READY_PRIORITY( uxPriority ) \
|
||||
{ \
|
||||
if( listCURRENT_LIST_LENGTH( &( pxReadyTasksLists[ ( uxPriority ) ] ) ) == ( UBaseType_t ) 0 ) \
|
||||
if( listCURRENT_LIST_LENGTH( &( pxReadyTasksLists[uxPsrId][ ( uxPriority ) ] ) ) == ( UBaseType_t ) 0 ) \
|
||||
{ \
|
||||
portRESET_READY_PRIORITY( ( uxPriority ), ( uxTopReadyPriority ) ); \
|
||||
portRESET_READY_PRIORITY( ( uxPriority ), ( uxTopReadyPriority[uxPsrId] ) ); \
|
||||
} \
|
||||
}
|
||||
|
||||
|
@ -1108,7 +1108,7 @@ void vAddNewTaskToCurrentReadyList(TaskHandle_t pxNewTaskHandle)
|
|||
#if ( configUSE_TRACE_FACILITY == 1 )
|
||||
{
|
||||
/* Add a counter into the TCB for tracing only. */
|
||||
pxNewTCB->uxTCBNumber = uxTaskNumber;
|
||||
pxNewTCB->uxTCBNumber = uxTaskNumber[uxPsrId];
|
||||
}
|
||||
#endif /* configUSE_TRACE_FACILITY */
|
||||
traceTASK_CREATE( pxNewTCB );
|
||||
|
@ -1979,7 +1979,7 @@ UBaseType_t uxPsrId = uxPortGetProcessorId();
|
|||
pxIdleTaskStackBuffer,
|
||||
pxIdleTaskTCBBuffer ); /*lint !e961 MISRA exception, justified as it is not a redundant explicit cast to all supported compilers. */
|
||||
|
||||
if( xIdleTaskHandle != NULL )
|
||||
if( xIdleTaskHandle[uxPsrId] != NULL )
|
||||
{
|
||||
xReturn = pdPASS;
|
||||
}
|
||||
|
@ -2073,7 +2073,7 @@ UBaseType_t uxPsrId = uxPortGetProcessorId();
|
|||
|
||||
/* Prevent compiler warnings if INCLUDE_xTaskGetIdleTaskHandle is set to 0,
|
||||
meaning xIdleTaskHandle is not used anywhere else. */
|
||||
( void ) xIdleTaskHandle;
|
||||
( void ) xIdleTaskHandle[uxPsrId];
|
||||
}
|
||||
/*-----------------------------------------------------------*/
|
||||
|
||||
|
@ -2412,7 +2412,7 @@ UBaseType_t uxPsrId = uxPortGetProcessorId();
|
|||
{
|
||||
UBaseType_t uxQueue = configMAX_PRIORITIES;
|
||||
TCB_t* pxTCB;
|
||||
|
||||
UBaseType_t uxPsrId = uxPortGetProcessorId();
|
||||
/* Task names will be truncated to configMAX_TASK_NAME_LEN - 1 bytes. */
|
||||
configASSERT( strlen( pcNameToQuery ) < configMAX_TASK_NAME_LEN );
|
||||
|
||||
|
@ -2422,7 +2422,7 @@ UBaseType_t uxPsrId = uxPortGetProcessorId();
|
|||
do
|
||||
{
|
||||
uxQueue--;
|
||||
pxTCB = prvSearchForNameWithinSingleList( ( List_t * ) &( pxReadyTasksLists[ uxQueue ] ), pcNameToQuery );
|
||||
pxTCB = prvSearchForNameWithinSingleList( ( List_t * ) &( pxReadyTasksLists[uxPsrId][ uxQueue ] ), pcNameToQuery );
|
||||
|
||||
if( pxTCB != NULL )
|
||||
{
|
||||
|
@ -2435,12 +2435,12 @@ UBaseType_t uxPsrId = uxPortGetProcessorId();
|
|||
/* Search the delayed lists. */
|
||||
if( pxTCB == NULL )
|
||||
{
|
||||
pxTCB = prvSearchForNameWithinSingleList( ( List_t * ) pxDelayedTaskList, pcNameToQuery );
|
||||
pxTCB = prvSearchForNameWithinSingleList( ( List_t * ) pxDelayedTaskList[uxPsrId], pcNameToQuery );
|
||||
}
|
||||
|
||||
if( pxTCB == NULL )
|
||||
{
|
||||
pxTCB = prvSearchForNameWithinSingleList( ( List_t * ) pxOverflowDelayedTaskList, pcNameToQuery );
|
||||
pxTCB = prvSearchForNameWithinSingleList( ( List_t * ) pxOverflowDelayedTaskList[uxPsrId], pcNameToQuery );
|
||||
}
|
||||
|
||||
#if ( INCLUDE_vTaskSuspend == 1 )
|
||||
|
@ -2448,7 +2448,7 @@ UBaseType_t uxPsrId = uxPortGetProcessorId();
|
|||
if( pxTCB == NULL )
|
||||
{
|
||||
/* Search the suspended list. */
|
||||
pxTCB = prvSearchForNameWithinSingleList( &xSuspendedTaskList, pcNameToQuery );
|
||||
pxTCB = prvSearchForNameWithinSingleList( &xSuspendedTaskList[uxPsrId], pcNameToQuery );
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
@ -2458,7 +2458,7 @@ UBaseType_t uxPsrId = uxPortGetProcessorId();
|
|||
if( pxTCB == NULL )
|
||||
{
|
||||
/* Search the deleted list. */
|
||||
pxTCB = prvSearchForNameWithinSingleList( &xTasksWaitingTermination, pcNameToQuery );
|
||||
pxTCB = prvSearchForNameWithinSingleList( &xTasksWaitingTermination[uxPsrId], pcNameToQuery );
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
@ -2476,31 +2476,31 @@ UBaseType_t uxPsrId = uxPortGetProcessorId();
|
|||
UBaseType_t uxTaskGetSystemState( TaskStatus_t * const pxTaskStatusArray, const UBaseType_t uxArraySize, uint32_t * const pulTotalRunTime )
|
||||
{
|
||||
UBaseType_t uxTask = 0, uxQueue = configMAX_PRIORITIES;
|
||||
|
||||
UBaseType_t uxPsrId = uxPortGetProcessorId();
|
||||
vTaskSuspendAll();
|
||||
{
|
||||
/* Is there a space in the array for each task in the system? */
|
||||
if( uxArraySize >= uxCurrentNumberOfTasks )
|
||||
if( uxArraySize >= uxCurrentNumberOfTasks[uxPsrId] )
|
||||
{
|
||||
/* Fill in an TaskStatus_t structure with information on each
|
||||
task in the Ready state. */
|
||||
do
|
||||
{
|
||||
uxQueue--;
|
||||
uxTask += prvListTasksWithinSingleList( &( pxTaskStatusArray[ uxTask ] ), &( pxReadyTasksLists[ uxQueue ] ), eReady );
|
||||
uxTask += prvListTasksWithinSingleList( &( pxTaskStatusArray[ uxTask ] ), &( pxReadyTasksLists[uxPsrId][ uxQueue ] ), eReady );
|
||||
|
||||
} while( uxQueue > ( UBaseType_t ) tskIDLE_PRIORITY ); /*lint !e961 MISRA exception as the casts are only redundant for some ports. */
|
||||
|
||||
/* Fill in an TaskStatus_t structure with information on each
|
||||
task in the Blocked state. */
|
||||
uxTask += prvListTasksWithinSingleList( &( pxTaskStatusArray[ uxTask ] ), ( List_t * ) pxDelayedTaskList, eBlocked );
|
||||
uxTask += prvListTasksWithinSingleList( &( pxTaskStatusArray[ uxTask ] ), ( List_t * ) pxOverflowDelayedTaskList, eBlocked );
|
||||
uxTask += prvListTasksWithinSingleList( &( pxTaskStatusArray[ uxTask ] ), ( List_t * ) pxDelayedTaskList[uxPsrId], eBlocked );
|
||||
uxTask += prvListTasksWithinSingleList( &( pxTaskStatusArray[ uxTask ] ), ( List_t * ) pxOverflowDelayedTaskList[uxPsrId], eBlocked );
|
||||
|
||||
#if( INCLUDE_vTaskDelete == 1 )
|
||||
{
|
||||
/* Fill in an TaskStatus_t structure with information on
|
||||
each task that has been deleted but not yet cleaned up. */
|
||||
uxTask += prvListTasksWithinSingleList( &( pxTaskStatusArray[ uxTask ] ), &xTasksWaitingTermination, eDeleted );
|
||||
uxTask += prvListTasksWithinSingleList( &( pxTaskStatusArray[ uxTask ] ), &xTasksWaitingTermination[uxPsrId], eDeleted );
|
||||
}
|
||||
#endif
|
||||
|
||||
|
@ -2508,7 +2508,7 @@ UBaseType_t uxPsrId = uxPortGetProcessorId();
|
|||
{
|
||||
/* Fill in an TaskStatus_t structure with information on
|
||||
each task in the Suspended state. */
|
||||
uxTask += prvListTasksWithinSingleList( &( pxTaskStatusArray[ uxTask ] ), &xSuspendedTaskList, eSuspended );
|
||||
uxTask += prvListTasksWithinSingleList( &( pxTaskStatusArray[ uxTask ] ), &xSuspendedTaskList[uxPsrId], eSuspended );
|
||||
}
|
||||
#endif
|
||||
|
||||
|
@ -2549,10 +2549,11 @@ UBaseType_t uxPsrId = uxPortGetProcessorId();
|
|||
|
||||
TaskHandle_t xTaskGetIdleTaskHandle( void )
|
||||
{
|
||||
UBaseType_t uxPsrId = uxPortGetProcessorId();
|
||||
/* If xTaskGetIdleTaskHandle() is called before the scheduler has been
|
||||
started, then xIdleTaskHandle will be NULL. */
|
||||
configASSERT( ( xIdleTaskHandle != NULL ) );
|
||||
return xIdleTaskHandle;
|
||||
configASSERT( ( xIdleTaskHandle[uxPsrId] != NULL ) );
|
||||
return xIdleTaskHandle[uxPsrId];
|
||||
}
|
||||
|
||||
#endif /* INCLUDE_xTaskGetIdleTaskHandle */
|
||||
|
@ -2942,9 +2943,9 @@ void vTaskSwitchContext( void )
|
|||
#if ( configGENERATE_RUN_TIME_STATS == 1 )
|
||||
{
|
||||
#ifdef portALT_GET_RUN_TIME_COUNTER_VALUE
|
||||
portALT_GET_RUN_TIME_COUNTER_VALUE( ulTotalRunTime );
|
||||
portALT_GET_RUN_TIME_COUNTER_VALUE( ulTotalRunTime[uxPsrId] );
|
||||
#else
|
||||
ulTotalRunTime = portGET_RUN_TIME_COUNTER_VALUE();
|
||||
ulTotalRunTime[uxPsrId] = portGET_RUN_TIME_COUNTER_VALUE();
|
||||
#endif
|
||||
|
||||
/* Add the amount of time the task has been running to the
|
||||
|
@ -2954,15 +2955,15 @@ void vTaskSwitchContext( void )
|
|||
overflows. The guard against negative values is to protect
|
||||
against suspect run time stat counter implementations - which
|
||||
are provided by the application, not the kernel. */
|
||||
if( ulTotalRunTime > ulTaskSwitchedInTime )
|
||||
if( ulTotalRunTime[uxPsrId] > ulTaskSwitchedInTime[uxPsrId] )
|
||||
{
|
||||
pxCurrentTCB->ulRunTimeCounter += ( ulTotalRunTime - ulTaskSwitchedInTime );
|
||||
pxCurrentTCB[uxPsrId]->ulRunTimeCounter += ( ulTotalRunTime[uxPsrId] - ulTaskSwitchedInTime[uxPsrId] );
|
||||
}
|
||||
else
|
||||
{
|
||||
mtCOVERAGE_TEST_MARKER();
|
||||
}
|
||||
ulTaskSwitchedInTime = ulTotalRunTime;
|
||||
ulTaskSwitchedInTime[uxPsrId] = ulTotalRunTime[uxPsrId];
|
||||
}
|
||||
#endif /* configGENERATE_RUN_TIME_STATS */
|
||||
|
||||
|
@ -3055,7 +3056,7 @@ void vTaskPlaceOnUnorderedEventList( List_t * pxEventList, const TickType_t xIte
|
|||
xTicksToWait = portMAX_DELAY;
|
||||
}
|
||||
|
||||
traceTASK_DELAY_UNTIL( ( xTickCount + xTicksToWait ) );
|
||||
traceTASK_DELAY_UNTIL( ( xTickCount[uxPsrId] + xTicksToWait ) );
|
||||
prvAddCurrentTaskToDelayedList( xTicksToWait, xWaitIndefinitely );
|
||||
}
|
||||
|
||||
|
@ -3513,6 +3514,7 @@ static portTASK_FUNCTION( prvIdleTask, pvParameters )
|
|||
void vTaskAllocateMPURegions( TaskHandle_t xTaskToModify, const MemoryRegion_t * const xRegions )
|
||||
{
|
||||
TCB_t *pxTCB;
|
||||
UBaseType_t uxPsrId = uxPortGetProcessorId();
|
||||
|
||||
/* If null is passed in here then we are modifying the MPU settings of
|
||||
the calling task. */
|
||||
|
@ -3592,7 +3594,7 @@ static void prvCheckTasksWaitingTermination( void )
|
|||
void vTaskGetInfo( TaskHandle_t xTask, TaskStatus_t *pxTaskStatus, BaseType_t xGetFreeStackSpace, eTaskState eState )
|
||||
{
|
||||
TCB_t *pxTCB;
|
||||
|
||||
UBaseType_t uxPsrId = uxPortGetProcessorId();
|
||||
/* xTask is NULL then get the state of the calling task. */
|
||||
pxTCB = prvGetTCBFromHandle( xTask );
|
||||
|
||||
|
@ -3627,7 +3629,7 @@ static void prvCheckTasksWaitingTermination( void )
|
|||
state is just set to whatever is passed in. */
|
||||
if( eState != eInvalid )
|
||||
{
|
||||
if( pxTCB == pxCurrentTCB )
|
||||
if( pxTCB == pxCurrentTCB[uxPsrId] )
|
||||
{
|
||||
pxTaskStatus->eCurrentState = eRunning;
|
||||
}
|
||||
|
@ -3869,7 +3871,7 @@ UBaseType_t uxPsrId = uxPortGetProcessorId();
|
|||
{
|
||||
BaseType_t xReturn;
|
||||
|
||||
if( xSchedulerRunning == pdFALSE )
|
||||
if( xSchedulerRunning[uxPortGetProcessorId()] == pdFALSE )
|
||||
{
|
||||
xReturn = taskSCHEDULER_NOT_STARTED;
|
||||
}
|
||||
|
@ -4270,7 +4272,7 @@ uint32_t mstatus_t = 0;
|
|||
TaskStatus_t *pxTaskStatusArray;
|
||||
volatile UBaseType_t uxArraySize, x;
|
||||
char cStatus;
|
||||
|
||||
UBaseType_t uxPsrId = uxPortGetProcessorId();
|
||||
/*
|
||||
* PLEASE NOTE:
|
||||
*
|
||||
|
@ -4301,12 +4303,12 @@ uint32_t mstatus_t = 0;
|
|||
|
||||
/* Take a snapshot of the number of tasks in case it changes while this
|
||||
function is executing. */
|
||||
uxArraySize = uxCurrentNumberOfTasks;
|
||||
uxArraySize = uxCurrentNumberOfTasks[uxPsrId];
|
||||
|
||||
/* Allocate an array index for each task. NOTE! if
|
||||
configSUPPORT_DYNAMIC_ALLOCATION is set to 0 then pvPortMalloc() will
|
||||
equate to NULL. */
|
||||
pxTaskStatusArray = pvPortMalloc( uxCurrentNumberOfTasks * sizeof( TaskStatus_t ) );
|
||||
pxTaskStatusArray = pvPortMalloc( uxCurrentNumberOfTasks[uxPsrId] * sizeof( TaskStatus_t ) );
|
||||
|
||||
if( pxTaskStatusArray != NULL )
|
||||
{
|
||||
|
@ -4368,7 +4370,7 @@ uint32_t mstatus_t = 0;
|
|||
TaskStatus_t *pxTaskStatusArray;
|
||||
volatile UBaseType_t uxArraySize, x;
|
||||
uint32_t ulTotalTime, ulStatsAsPercentage;
|
||||
|
||||
UBaseType_t uxPsrId = uxPortGetProcessorId();
|
||||
#if( configUSE_TRACE_FACILITY != 1 )
|
||||
{
|
||||
#error configUSE_TRACE_FACILITY must also be set to 1 in FreeRTOSConfig.h to use vTaskGetRunTimeStats().
|
||||
|
@ -4405,12 +4407,12 @@ uint32_t mstatus_t = 0;
|
|||
|
||||
/* Take a snapshot of the number of tasks in case it changes while this
|
||||
function is executing. */
|
||||
uxArraySize = uxCurrentNumberOfTasks;
|
||||
uxArraySize = uxCurrentNumberOfTasks[uxPsrId];
|
||||
|
||||
/* Allocate an array index for each task. NOTE! If
|
||||
configSUPPORT_DYNAMIC_ALLOCATION is set to 0 then pvPortMalloc() will
|
||||
equate to NULL. */
|
||||
pxTaskStatusArray = pvPortMalloc( uxCurrentNumberOfTasks * sizeof( TaskStatus_t ) );
|
||||
pxTaskStatusArray = pvPortMalloc( uxCurrentNumberOfTasks[uxPsrId] * sizeof( TaskStatus_t ) );
|
||||
|
||||
if( pxTaskStatusArray != NULL )
|
||||
{
|
||||
|
@ -5107,24 +5109,24 @@ const TickType_t xConstTickCount = xTickCount[uxPsrId];
|
|||
xTimeToWake = xConstTickCount + xTicksToWait;
|
||||
|
||||
/* The list item will be inserted in wake time order. */
|
||||
listSET_LIST_ITEM_VALUE( &( pxCurrentTCB->xStateListItem ), xTimeToWake );
|
||||
listSET_LIST_ITEM_VALUE( &( pxCurrentTCB[uxPsrId]->xStateListItem ), xTimeToWake );
|
||||
|
||||
if( xTimeToWake < xConstTickCount )
|
||||
{
|
||||
/* Wake time has overflowed. Place this item in the overflow list. */
|
||||
vListInsert( pxOverflowDelayedTaskList, &( pxCurrentTCB->xStateListItem ) );
|
||||
vListInsert( pxOverflowDelayedTaskList[uxPsrId], &( pxCurrentTCB[uxPsrId]->xStateListItem ) );
|
||||
}
|
||||
else
|
||||
{
|
||||
/* The wake time has not overflowed, so the current block list is used. */
|
||||
vListInsert( pxDelayedTaskList, &( pxCurrentTCB->xStateListItem ) );
|
||||
vListInsert( pxDelayedTaskList[uxPsrId], &( pxCurrentTCB[uxPsrId]->xStateListItem ) );
|
||||
|
||||
/* If the task entering the blocked state was placed at the head of the
|
||||
list of blocked tasks then xNextTaskUnblockTime needs to be updated
|
||||
too. */
|
||||
if( xTimeToWake < xNextTaskUnblockTime )
|
||||
if( xTimeToWake < xNextTaskUnblockTime[uxPsrId] )
|
||||
{
|
||||
xNextTaskUnblockTime = xTimeToWake;
|
||||
xNextTaskUnblockTime[uxPsrId] = xTimeToWake;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
|
@ -0,0 +1,51 @@
|
|||
/* Copyright 2018 Canaan Inc.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#ifndef _POSIX_SYS_IOCTL_H
|
||||
#define _POSIX_SYS_IOCTL_H
|
||||
|
||||
#include <stddef.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C"
|
||||
{
|
||||
#endif
|
||||
|
||||
#define IOCPARM_MASK 0x7fU /* parameters must be < 128 bytes */
|
||||
#define IOC_VOID 0x20000000UL /* no parameters */
|
||||
#define IOC_OUT 0x40000000UL /* copy out parameters */
|
||||
#define IOC_IN 0x80000000UL /* copy in parameters */
|
||||
#define IOC_INOUT (IOC_IN | IOC_OUT) /* 0x20000000 distinguishes new & old ioctl's */
|
||||
#define _IO(x, y) (IOC_VOID | ((x) << 8) | (y))
|
||||
|
||||
#define _IOR(x, y, t) (IOC_OUT | (((unsigned int)sizeof(t) & IOCPARM_MASK) << 16) | ((x) << 8) | (y))
|
||||
|
||||
#define _IOW(x, y, t) (IOC_IN | (((unsigned int)sizeof(t) & IOCPARM_MASK) << 16) | ((x) << 8) | (y))
|
||||
|
||||
#ifndef FIONREAD
|
||||
#define FIONREAD _IOR('f', 127, unsigned int) /* get # bytes to read */
|
||||
#endif
|
||||
#ifndef FIONBIO
|
||||
#define FIONBIO _IOW('f', 126, unsigned int) /* set/clear non-blocking i/o */
|
||||
#endif
|
||||
|
||||
int ioctl(int handle, unsigned int cmd, void *argp);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -0,0 +1,46 @@
|
|||
/* Copyright 2018 Canaan Inc.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
#include "sys/ioctl.h"
|
||||
#include "utils.h"
|
||||
#include <kernel/driver_impl.hpp>
|
||||
#include <network.h>
|
||||
#include <string.h>
|
||||
#include <sys/socket.h>
|
||||
|
||||
using namespace sys;
|
||||
|
||||
#define CATCH_ALL \
|
||||
catch (errno_exception &e) \
|
||||
{ \
|
||||
errno = e.code(); \
|
||||
return -1; \
|
||||
}
|
||||
|
||||
int ioctl(int handle, unsigned int cmd, void *argp)
|
||||
{
|
||||
try
|
||||
{
|
||||
auto &obj = system_handle_to_object(handle); \
|
||||
configASSERT(obj.is<custom_driver>()); \
|
||||
auto f = obj.as<custom_driver>();
|
||||
|
||||
const int val = *(int *)argp;
|
||||
f->control((uint32_t)cmd, { (const uint8_t *)&val, 4L }, { NULL, 0L });
|
||||
|
||||
return 0;
|
||||
}
|
||||
CATCH_ALL;
|
||||
}
|
||||
|
|
@ -17,6 +17,7 @@
|
|||
#include <kernel/driver_impl.hpp>
|
||||
#include <network.h>
|
||||
#include <string.h>
|
||||
#include <sys/select.h>
|
||||
|
||||
using namespace sys;
|
||||
|
||||
|
@ -26,7 +27,11 @@ using namespace sys;
|
|||
auto f = obj.as<network_socket>();
|
||||
|
||||
#define CATCH_ALL \
|
||||
catch (...) { return -1; }
|
||||
catch (errno_exception & e) \
|
||||
{ \
|
||||
errno = e.code(); \
|
||||
return -1; \
|
||||
}
|
||||
|
||||
#define CHECK_ARG(x) \
|
||||
if (!x) \
|
||||
|
@ -279,3 +284,16 @@ int sendto(int socket, const void *data, size_t size, int flags, const struct so
|
|||
}
|
||||
CATCH_ALL;
|
||||
}
|
||||
|
||||
int select(int maxfdp1, fd_set *readset, fd_set *writeset, fd_set *exceptset, struct timeval *timeout)
|
||||
{
|
||||
try
|
||||
{
|
||||
int socket = maxfdp1 - 1;
|
||||
SOCKET_ENTRY;
|
||||
|
||||
f->select(readset, writeset, exceptset, timeout);
|
||||
return 0;
|
||||
}
|
||||
CATCH_ALL;
|
||||
}
|
||||
|
|
|
@ -522,14 +522,14 @@ alloc_socket(struct netconn *newconn, int accepted)
|
|||
after having marked it as used. */
|
||||
SYS_ARCH_UNPROTECT(lev);
|
||||
sockets[i].lastdata.pbuf = NULL;
|
||||
#if LWIP_SOCKET_SELECT
|
||||
#if LWIP_SOCKET_SELECT || LWIP_SOCKET_POLL
|
||||
LWIP_ASSERT("sockets[i].select_waiting == 0", sockets[i].select_waiting == 0);
|
||||
sockets[i].rcvevent = 0;
|
||||
/* TCP sendbuf is empty, but the socket is not yet writable until connected
|
||||
* (unless it has been created by accept()). */
|
||||
sockets[i].sendevent = (NETCONNTYPE_GROUP(newconn->type) == NETCONN_TCP ? (accepted != 0) : 1);
|
||||
sockets[i].errevent = 0;
|
||||
#endif /* LWIP_SOCKET_SELECT */
|
||||
#endif /* LWIP_SOCKET_SELECT || LWIP_SOCKET_POLL */
|
||||
return i + LWIP_SOCKET_OFFSET;
|
||||
}
|
||||
SYS_ARCH_UNPROTECT(lev);
|
||||
|
@ -1305,7 +1305,7 @@ lwip_recvmsg(int s, struct msghdr *message, int flags)
|
|||
if ((message->msg_iov[i].iov_base == NULL) || ((ssize_t)message->msg_iov[i].iov_len <= 0) ||
|
||||
((size_t)(ssize_t)message->msg_iov[i].iov_len != message->msg_iov[i].iov_len) ||
|
||||
((ssize_t)(buflen + (ssize_t)message->msg_iov[i].iov_len) <= 0)) {
|
||||
sock_set_errno(sock, ERR_VAL);
|
||||
sock_set_errno(sock, err_to_errno(ERR_VAL));
|
||||
done_socket(sock);
|
||||
return -1;
|
||||
}
|
||||
|
@ -2304,7 +2304,6 @@ lwip_poll_dec_sockets_used(struct pollfd *fds, nfds_t nfds)
|
|||
/* Go through each struct pollfd in the array. */
|
||||
for (fdi = 0; fdi < nfds; fdi++) {
|
||||
struct lwip_sock *sock = tryget_socket_unconn_nouse(fds[fdi].fd);
|
||||
LWIP_ASSERT("socket gone at the end of select", sock != NULL);
|
||||
if (sock != NULL) {
|
||||
done_socket(sock);
|
||||
}
|
||||
|
@ -3741,7 +3740,7 @@ lwip_setsockopt_impl(int s, int level, int optname, const void *optval, socklen_
|
|||
}
|
||||
|
||||
int
|
||||
lwip_ioctl(int s, long cmd, void *argp)
|
||||
lwip_ioctl(int s, unsigned int cmd, void *argp)
|
||||
{
|
||||
struct lwip_sock *sock = get_socket(s);
|
||||
u8_t val;
|
||||
|
@ -3808,7 +3807,7 @@ lwip_ioctl(int s, long cmd, void *argp)
|
|||
#endif /* LWIP_SO_RCVBUF */
|
||||
#endif /* LWIP_SO_RCVBUF || LWIP_FIONREAD_LINUXMODE */
|
||||
|
||||
case (long)FIONBIO:
|
||||
case FIONBIO:
|
||||
val = 0;
|
||||
if (argp && *(int *)argp) {
|
||||
val = 1;
|
||||
|
|
|
@ -214,7 +214,7 @@ ip4_route(const ip4_addr_t *dest)
|
|||
#endif /* !LWIP_SINGLE_NETIF */
|
||||
|
||||
if ((netif_default == NULL) || !netif_is_up(netif_default) || !netif_is_link_up(netif_default) ||
|
||||
ip4_addr_isany_val(*netif_ip4_addr(netif_default))) {
|
||||
ip4_addr_isany_val(*netif_ip4_addr(netif_default)) || ip4_addr_isloopback(dest)) {
|
||||
/* No matching netif found and default netif is not usable.
|
||||
If this is not good enough for you, use LWIP_HOOK_IP4_ROUTE() */
|
||||
LWIP_DEBUGF(IP_DEBUG | LWIP_DBG_LEVEL_SERIOUS, ("ip4_route: No route to %"U16_F".%"U16_F".%"U16_F".%"U16_F"\n",
|
||||
|
|
|
@ -583,6 +583,7 @@ tcp_abandon(struct tcp_pcb *pcb, int reset)
|
|||
tcp_free(pcb);
|
||||
} else {
|
||||
int send_rst = 0;
|
||||
u16_t local_port = 0;
|
||||
enum tcp_state last_state;
|
||||
seqno = pcb->snd_nxt;
|
||||
ackno = pcb->rcv_nxt;
|
||||
|
@ -597,6 +598,7 @@ tcp_abandon(struct tcp_pcb *pcb, int reset)
|
|||
}
|
||||
} else {
|
||||
send_rst = reset;
|
||||
local_port = pcb->local_port;
|
||||
TCP_PCB_REMOVE_ACTIVE(pcb);
|
||||
}
|
||||
if (pcb->unacked != NULL) {
|
||||
|
@ -613,7 +615,7 @@ tcp_abandon(struct tcp_pcb *pcb, int reset)
|
|||
tcp_backlog_accepted(pcb);
|
||||
if (send_rst) {
|
||||
LWIP_DEBUGF(TCP_RST_DEBUG, ("tcp_abandon: sending RST\n"));
|
||||
tcp_rst(pcb, seqno, ackno, &pcb->local_ip, &pcb->remote_ip, pcb->local_port, pcb->remote_port);
|
||||
tcp_rst(pcb, seqno, ackno, &pcb->local_ip, &pcb->remote_ip, local_port, pcb->remote_port);
|
||||
}
|
||||
last_state = pcb->state;
|
||||
tcp_free(pcb);
|
||||
|
@ -966,6 +968,7 @@ void
|
|||
tcp_recved(struct tcp_pcb *pcb, u16_t len)
|
||||
{
|
||||
u32_t wnd_inflation;
|
||||
tcpwnd_size_t rcv_wnd;
|
||||
|
||||
LWIP_ASSERT_CORE_LOCKED();
|
||||
|
||||
|
@ -975,19 +978,13 @@ tcp_recved(struct tcp_pcb *pcb, u16_t len)
|
|||
LWIP_ASSERT("don't call tcp_recved for listen-pcbs",
|
||||
pcb->state != LISTEN);
|
||||
|
||||
pcb->rcv_wnd = (tcpwnd_size_t)(pcb->rcv_wnd + len);
|
||||
if (pcb->rcv_wnd > TCP_WND_MAX(pcb)) {
|
||||
pcb->rcv_wnd = TCP_WND_MAX(pcb);
|
||||
} else if (pcb->rcv_wnd == 0) {
|
||||
/* rcv_wnd overflowed */
|
||||
if (TCP_STATE_IS_CLOSING(pcb->state)) {
|
||||
/* In passive close, we allow this, since the FIN bit is added to rcv_wnd
|
||||
by the stack itself, since it is not mandatory for an application
|
||||
to call tcp_recved() for the FIN bit, but e.g. the netconn API does so. */
|
||||
rcv_wnd = (tcpwnd_size_t)(pcb->rcv_wnd + len);
|
||||
if ((rcv_wnd > TCP_WND_MAX(pcb)) || (rcv_wnd < pcb->rcv_wnd)) {
|
||||
/* window got too big or tcpwnd_size_t overflow */
|
||||
LWIP_DEBUGF(TCP_DEBUG, ("tcp_recved: window got too big or tcpwnd_size_t overflow\n"));
|
||||
pcb->rcv_wnd = TCP_WND_MAX(pcb);
|
||||
} else {
|
||||
LWIP_ASSERT("tcp_recved: len wrapped rcv_wnd\n", 0);
|
||||
}
|
||||
pcb->rcv_wnd = rcv_wnd;
|
||||
}
|
||||
|
||||
wnd_inflation = tcp_update_rcv_ann_wnd(pcb);
|
||||
|
@ -1219,6 +1216,7 @@ tcp_slowtmr_start:
|
|||
LWIP_ASSERT("tcp_slowtmr: active pcb->state != TIME-WAIT\n", pcb->state != TIME_WAIT);
|
||||
if (pcb->last_timer == tcp_timer_ctr) {
|
||||
/* skip this pcb, we have already processed it */
|
||||
prev = pcb;
|
||||
pcb = pcb->next;
|
||||
continue;
|
||||
}
|
||||
|
|
|
@ -1290,7 +1290,7 @@
|
|||
* an upper limit on the MSS advertised by the remote host.
|
||||
*/
|
||||
#if !defined TCP_MSS || defined __DOXYGEN__
|
||||
#define TCP_MSS 536
|
||||
#define TCP_MSS 1536
|
||||
#endif
|
||||
|
||||
/**
|
||||
|
@ -1763,7 +1763,7 @@
|
|||
* sys_thread_new() when the thread is created.
|
||||
*/
|
||||
#if !defined TCPIP_THREAD_PRIO || defined __DOXYGEN__
|
||||
#define TCPIP_THREAD_PRIO 1
|
||||
#define TCPIP_THREAD_PRIO 2
|
||||
#endif
|
||||
|
||||
/**
|
||||
|
|
|
@ -407,27 +407,27 @@ typedef struct ipv6_mreq {
|
|||
#define IOC_INOUT (IOC_IN|IOC_OUT)
|
||||
/* 0x20000000 distinguishes new &
|
||||
old ioctl's */
|
||||
#define _IO(x,y) ((long)(IOC_VOID|((x)<<8)|(y)))
|
||||
#define _IO(x,y) ((unsigned int)(IOC_VOID|((x)<<8)|(y)))
|
||||
|
||||
#define _IOR(x,y,t) ((long)(IOC_OUT|((sizeof(t)&IOCPARM_MASK)<<16)|((x)<<8)|(y)))
|
||||
#define _IOR(x,y,t) ((unsigned int)(IOC_OUT|((sizeof(t)&IOCPARM_MASK)<<16)|((x)<<8)|(y)))
|
||||
|
||||
#define _IOW(x,y,t) ((long)(IOC_IN|((sizeof(t)&IOCPARM_MASK)<<16)|((x)<<8)|(y)))
|
||||
#define _IOW(x,y,t) ((unsigned int)(IOC_IN|((sizeof(t)&IOCPARM_MASK)<<16)|((x)<<8)|(y)))
|
||||
#endif /* !defined(FIONREAD) || !defined(FIONBIO) */
|
||||
|
||||
#ifndef FIONREAD
|
||||
#define FIONREAD _IOR('f', 127, unsigned long) /* get # bytes to read */
|
||||
#define FIONREAD _IOR('f', 127, unsigned int) /* get # bytes to read */
|
||||
#endif
|
||||
#ifndef FIONBIO
|
||||
#define FIONBIO _IOW('f', 126, unsigned long) /* set/clear non-blocking i/o */
|
||||
#define FIONBIO _IOW('f', 126, unsigned int) /* set/clear non-blocking i/o */
|
||||
#endif
|
||||
|
||||
/* Socket I/O Controls: unimplemented */
|
||||
#ifndef SIOCSHIWAT
|
||||
#define SIOCSHIWAT _IOW('s', 0, unsigned long) /* set high watermark */
|
||||
#define SIOCGHIWAT _IOR('s', 1, unsigned long) /* get high watermark */
|
||||
#define SIOCSLOWAT _IOW('s', 2, unsigned long) /* set low watermark */
|
||||
#define SIOCGLOWAT _IOR('s', 3, unsigned long) /* get low watermark */
|
||||
#define SIOCATMARK _IOR('s', 7, unsigned long) /* at oob mark? */
|
||||
#define SIOCSHIWAT _IOW('s', 0, unsigned int) /* set high watermark */
|
||||
#define SIOCGHIWAT _IOR('s', 1, unsigned int) /* get high watermark */
|
||||
#define SIOCSLOWAT _IOW('s', 2, unsigned int) /* set low watermark */
|
||||
#define SIOCGLOWAT _IOR('s', 3, unsigned int) /* get low watermark */
|
||||
#define SIOCATMARK _IOR('s', 7, unsigned int) /* at oob mark? */
|
||||
#endif
|
||||
|
||||
/* commands for fnctl */
|
||||
|
@ -603,7 +603,7 @@ int lwip_select(int maxfdp1, fd_set *readset, fd_set *writeset, fd_set *exceptse
|
|||
#if LWIP_SOCKET_POLL
|
||||
int lwip_poll(struct pollfd *fds, nfds_t nfds, int timeout);
|
||||
#endif
|
||||
int lwip_ioctl(int s, long cmd, void *argp);
|
||||
int lwip_ioctl(int s, unsigned int cmd, void *argp);
|
||||
int lwip_fcntl(int s, int cmd, int val);
|
||||
const char *lwip_inet_ntop(int af, const void *src, char *dst, socklen_t size);
|
||||
int lwip_inet_pton(int af, const char *src, void *dst);
|
||||
|
|
Loading…
Reference in New Issue