initial commit

This commit is contained in:
2024-12-15 00:34:01 +06:00
commit 31efbc726f
1576 changed files with 657692 additions and 0 deletions

View File

@@ -0,0 +1,330 @@
#include <stdio.h>
#include "log_service.h"
#include "cmsis_os.h"
#include <platform/platform_stdlib.h>
#if CONFIG_JOYLINK
#if 1
void fATCJ(void *arg)
{
extern void joylink_erase(void);
printf("\r\n[ATCJ] Erase wifi and joylink info.");
if(arg){
printf("\r\n[ATCJ]Usage : ATCJ");
return;
}
joylink_erase();
}
// set joylink wifi config mode
void fATJM(void *arg)
{
extern int jl_wifi_config_mode;
printf("\nset joylink wifi config mode: softap\n");
if(arg){
printf("[ATCJ]Usage : ATJM\n");
return;
}
jl_wifi_config_mode = 1;
}
#else
void fATCJ(void *arg)
{
extern void cmd_jd_smart(int argc, char **argv);
int argc;
char *argv[MAX_ARGC] = {0};
printf("[ATCJ]:simple config command for jdsmart\n\r");
if(!arg){
printf("[ATCJ]Usage: ATCJ=simple_config\n\r");
return;
}
argv[0] = "simple_config";
if((argc = parse_param(arg, argv)) > 1){
cmd_jd_smart(argc, argv);
}
else
printf("[ATCJ]Usage: ATCJ=simple_config\n\r");
}
#endif
#endif
#if CONFIG_GAGENT
void fATCG(void *arg)
{
example_gagent();
}
void fATCE(void *arg)
{//Erase gagent config flash
extern int GAgent_DevEraseConfigData();
GAgent_DevEraseConfigData();
}
#endif
#if CONFIG_QQ_LINK
void fATCQ(void *arg)
{
int argc;
unsigned char *argv[MAX_ARGC] = {0};
extern void device_write_sn_license(int argc, unsigned char **argv);
extern void device_erase_all(int argc, unsigned char **argv);
if(!arg)
{
printf("\r\n[ATCQ] Write sn/license into flash or Erase all info\r\n");
printf("\r\n[ATCQ] Usage: ATCQ=erase");
printf("\r\n[ATCQ] Usage: ATCQ=sn,xxxxxxxx\r\n ATCQ=licensepart1,xxxxxxxx\r\n ATCQ=licensepart2,xxxxxxxx");
return;
}
argv[0] = "sn&&license&&erase";
argc = parse_param(arg, argv);
if(argc == 3) // Write sn&&license
{
device_write_sn_license(argc, argv);
}
else if(argc == 2) // Erase all info : ATCQ=erase
{
device_erase_all(argc, argv);
}
else
{
printf("\r\n[ATCQ] Usage: ATCQ=erase");
printf("\r\n[ATCQ]Usage: ATCQ=sn,xxxxxxxx\r\n ATCQ=licensepart1,xxxxxxxx\r\n ATCQ=licensepart2,xxxxxxxx");
}
}
#endif
#if CONFIG_AIRKISS_CLOUD
void fATCW(void *arg)
{
int argc;
unsigned char *argv[MAX_ARGC] = {0};
extern void airkiss_cloud_write_device_info(int argc, unsigned char **argv);
extern void airkiss_cloud_erase_ap_profile(int argc, unsigned char **argv);
if(!arg) goto USAGE;
argv[0] = "type/id/licese/erase";
argc = parse_param(arg, argv);
if(argc == 3) // Write typw/id/license
{
airkiss_cloud_write_device_info(argc, argv);
return;
}
else if(argc == 2) // Erase wifi profile : ATCW=erase
{
airkiss_cloud_erase_ap_profile(argc, argv);
return;
}
else
goto USAGE;
USAGE:
printf("\r\n[ATCW] Write ORDERLY device's type/id/license into flash or Erase wifi profile");
printf("\r\n[ATCW] Usage: ATCW=type,xxxxxxxx");
printf("\r\n[ATCW] Usage: ATCW=id,xxxxxxxx");
printf("\r\n[ATCW] Usage: ATCW=licensepart1,xxxxxxxx\t(80-Byte long)");
printf("\r\n[ATCW] Usage: ATCW=licensepart2,xxxxxxxx\t(80-Byte long)");
printf("\r\n[ATCW] Usage: ATCW=erase");
return;
}
#endif
#if CONFIG_ALINK
extern int alink_erase_wifi_config();
extern void alink_reset_to_factory(void *arg);
extern int alink_write_device_info(int argc, unsigned char **argv);
extern void alink_set_log_level(int argc, unsigned char **argv);
void fATCA(void *arg)
{
int argc;
int ret = -1;
unsigned char *argv[MAX_ARGC] = {0};
if(!arg) {
goto USAGE;
}
argv[0] = "k/s/l/e/r";
argc = parse_param(arg, argv);
if (argc == 3) {
/*Set log level: ATCA=l, trace/debug/info/warn/fatal/none
if set wrong, set info level by default*/
if (!strcmp(argv[1], "l")) {
alink_set_log_level(argc, argv);
return;
} else {
/* Write device key/device secret */
ret = alink_write_device_info(argc, argv);
if (ret) {
goto USAGE;
}
return;
}
} else if (argc == 2) {
/* Erase wifi profile or reset user account binding : "ATCA=e" or "ATCA=r" */
if (!strcmp(argv[1], "e")) {
alink_erase_wifi_config();
}else if(!strcmp(argv[1], "r")) {
alink_reset_to_factory(NULL);
}
}
USAGE:
printf("\r\n[ATCA] Write ORDERLY device's key/secret into flash, set log level or erase wifi profile");
printf("\r\n[ATCA] Usage: ATCA=k,xxxxxxxx\t(set device key, 20-Byte long)");
printf("\r\n[ATCA] Usage: ATCA=s,xxxxxxxx\t(set device secret, 32-Byte long)");
printf("\r\n[ATCA] Usage: ATCA=l,xxxx\t(set log level, trace/debug/info/warn/error/fatal/none)");
printf("\r\n[ATCA] Usage: ATCA=e\t(erase AP profile)");
printf("\r\n[ATCA] Usage: ATCA=r\t(reset user account binding)");
return;
}
void fATCZ(void *arg)
{
//Erase alink config flash
alink_erase_wifi_config();
}
void fATCT(void *arg)
{
alink_reset_to_factory(NULL);
}
#endif
#if (defined(CONFIG_RIC) && CONFIG_RIC)
#include "ric/ric_device.h"
#include "ric/ric_dev_ota_rtl8710b.h"
void fATCR(void *arg)
{
#if 0
int argc;
unsigned char len1, len2;
unsigned char *argv[MAX_ARGC] = {0};
argv[0] = "ricloud";
argc = parse_param(arg, argv);
if(argc == 2 && !strcmp("ota", argv[1])) {
ric_ota_v v = {0};
v.loop = 0;
ric_dev_msg_dump(MSG_OTA_REQ, (void *)&v);
}else if(argc == 3 && !strcmp("ota", argv[1]) && (!strcmp("0", argv[2]) || !strcmp("1", argv[2]))) {
ric_ota_v v = {0};
v.loop = *argv[2] - '0';
ric_dev_msg_dump(MSG_OTA_REQ, (void *)&v);
}else if(argc == 3 && !strcmp("ota", argv[1]) && !strcmp("s", argv[2])) {
ric_dev_msg_dump(MSG_OTA_STP, NULL);
}else if(argc == 4 && !strcmp("ota", argv[1]) && (!strcmp("0", argv[2]) || !strcmp("1", argv[2]))) {
ric_ota_v v = {0};
v.loop = *argv[2] - '0';
if(strlen(argv[3]) > sizeof(v.nv_num) -1) {
printf("\r\n[ATCR] error: the new version num should no longer than %d !", sizeof(v.nv_num) - 1);
}else {
strcpy(v.nv_num, argv[3]);
ric_dev_msg_dump(MSG_OTA_REQ, (void *)&v);
}
}else {
goto USAGE;
}
return;
USAGE:
printf("\r\n[ATCR] Control ameba operation to RICloud");
printf("\r\n[ATCR] Usage: ATCR=ota[,loop] ==>ota with default expected fw version num for one time [or one(loop:0) / infinite(loop:1) time(s)]");
printf("\r\n[ATCR] Usage: ATCR=ota,loop,version ==>ota with specified fw version num(version) for one(loop:0) or infinite(loop:1) time(s)");
printf("\r\n[ATCR] Usage: ATCR=ota,s ==>stop the infinite ota if it's started before");
return;
#endif
}
extern int ric_set_userid(char *);
extern int ric_set_server_ip(char *);
extern void ric_flash_erase_sector(uint32_t address);
void fATUS(void *arg)
{
int argc;
char *argv[MAX_ARGC] = {0};
argv[0] = "ricloud";
argc = parse_param(arg,argv);
if(argc == 3){
if(!strcmp("userid",argv[1]))
{
ric_set_userid(argv[2]);
}else if(!strcmp("svrip",argv[1])){
ric_set_server_ip(argv[2]);
}
}else if(argc == 2){
if(!strcmp("erase",argv[1])){
ric_flash_erase_sector(CONFIG_USER_INFO);
}
}else{
goto USAGE;
}
return;
USAGE:
printf("\r\n[ATUS] Setup User and Server info RICloud");
printf("\r\n[ATUS] Usage: ATUS=userid,xxxx ==>set registed user id");
printf("\r\n[ATUS] Usage: ATUS=svrip,xxx.xxx.xxx.xxx ==>set ricloud server ip address");
printf("\r\n[ATUS] Usage: ATUS=erase ==>erase user id and server ip address");
return;
}
#endif
void fATCx(void *arg)
{
}
#if CONFIG_GREE
extern void gree_erase_wifi_config();
void fATCR(void *arg)
{
gree_erase_wifi_config();
}
#endif
log_item_t at_cloud_items[ ] = {
#if CONFIG_JOYLINK
{"ATCJ", fATCJ,},
{"ATJM", fATJM,},
#endif
#if CONFIG_GAGENT
{"ATCG", fATCG,},
{"ATCE", fATCE,},
#endif
#if CONFIG_QQ_LINK
{"ATCQ", fATCQ,},
#endif
#if CONFIG_AIRKISS_CLOUD
{"ATCW", fATCW},
#endif
#if CONFIG_ALINK
{"ATCA", fATCA,},
{"ATCZ", fATCZ,},
{"ATCT", fATCT,},
#endif
#if CONFIG_GREE
{"ATCR", fATCR,},
#endif
#if (defined(CONFIG_RIC) && CONFIG_RIC)
{"ATCR", fATCR,},
{"ATUS", fATUS,},
#endif
{"ATC?", fATCx,},
};
void at_cloud_init(void)
{
log_service_add_table(at_cloud_items, sizeof(at_cloud_items)/sizeof(at_cloud_items[0]));
}
#if SUPPORT_LOG_SERVICE
log_module_init(at_cloud_init);
#endif

View File

@@ -0,0 +1,91 @@
#include <stdio.h>
#include "log_service.h"
#include "platform_opts.h"
#include <lwip_netconf.h>
#include "cmsis_os.h"
#include <platform/platform_stdlib.h>
#include <lwip/sockets.h>
#include <lwip/tcpip.h>
#define _AT_DHCP_ETHERNET_MII_ "ATE0"
#define _AT_SET_DEFAULT_INTERFACE "ATE1"
#if CONFIG_ETHERNET
extern int dhcp_ethernet_mii;
extern int ethernet_if_default;
extern struct netif xnetif[NET_IF_NUM];
void fATE0(void *arg)
{
int argc;
char *argv[MAX_ARGC] = {0};
printf("[ATE0]:DHCP configure for ethernet\n\r");
if(!arg){
printf("[ATE0]Usage to disable DHCP: ATE0=0\n");
printf("[ATE0]Usage to enable DHCP: ATE0=1\n");
return;
}
if('0' == *(char *)arg)
{
dhcp_ethernet_mii = 0;
}
else if('1' == *(char *)arg)
{
dhcp_ethernet_mii = 1;
LwIP_DHCP(NET_IF_NUM - 1, DHCP_START);
}
else
{
printf("[ATE0]Usage to disable DHCP: ATE0=0\n");
printf("[ATE0]Usage to enable DHCP: ATE0=1\n");
}
}
void fATE1(void *arg)
{
int argc;
char *argv[MAX_ARGC] = {0};
printf("[ATE1]:Set/check the default interface\n\r");
if(!arg){
if(ethernet_if_default)
printf("Ethernet is the default interface\n");
else
printf("wlan is the default interface\n");
return;
}
if('0' == *(char *)arg)
{
ethernet_if_default = 0;
printf("wlan is set to the default interface\n");
}
else if('1' == *(char *)arg)
{
ethernet_if_default = 1;
printf("ethernet is set to the default interface\n");
}
else
{
printf("[ATE0]Usage to check the default interface: ATE1\n");
printf("[ATE0]Usage to set ethernet as default interface: ATE1=1\n");
printf("[ATE0]Usage to set wlan as default interface: ATE1=0\n");
}
}
log_item_t at_ethernet_items[ ] = {
{"ATE0", fATE0,},
{"ATE1", fATE1,}
};
void at_ethernet_init(void)
{
log_service_add_table(at_ethernet_items, sizeof(at_ethernet_items)/sizeof(at_ethernet_items[0]));
}
log_module_init(at_ethernet_init);
#endif

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,105 @@
#ifndef __ATCMD_LWIP_H__
#define __ATCMD_LWIP_H__
#include "main.h"
#include "osdep_service.h"
#include <lwip/opt.h>
#include "lwip/sockets.h"
#include "lwip/api.h"
#include "lwip/sys.h"
#include "lwip/igmp.h"
#include "lwip/inet.h"
#include "lwip/tcp.h"
#include "lwip/raw.h"
#include "lwip/udp.h"
#include "lwip/tcpip.h"
#include "lwip/pbuf.h"
#include "lwip/netdb.h"
#include "lwip_netconf.h"
#define _AT_TRANSPORT_MODE_ "ATP1"
#define _AT_TRANSPORT_LOCAL_PORT_ "ATP2"
#define _AT_TRANSPORT_REMOTE_IP_ "ATP3"
#define _AT_TRANSPORT_REMOTE_PORT_ "ATP4"
#define _AT_TRANSPORT_START_SERVER_ "ATP5"
#define _AT_TRANSPORT_START_CLIENT_ "ATP6"
#define _AT_TRANSPORT_SHOW_SETTING_ "ATP?"
#define _AT_TRANSPORT_RECEIVE_DATA_ "ATR0"
#define _AT_TRANSPORT_RECEIVE_PACKET_SIZE_ "ATR1"
#define _AT_TRANSPORT_WRITE_DATA_ "ATRA"
#define _AT_TRANSPORT_WRITE_PACKET_SIZE_ "ATRB"
#define NODE_MODE_TCP 0
#define NODE_MODE_UDP 1
#define NODE_MODE_SSL 2
#define NODE_ROLE_SERVER 0
#define NODE_ROLE_CLIENT 1
#define NODE_ROLE_SEED 2
#define INVALID_SOCKET_ID (-1)
//parameters
#ifndef NET_IF_NUM
#define NET_IF_NUM 2
#endif
#define ATCMD_LWIP_TASK_PRIORITY (tskIDLE_PRIORITY + 1)
#if ATCMD_VER == ATVER_2
#ifndef ATCMD_SUPPORT_SSL
#define ATCMD_SUPPORT_SSL 0
#endif
#define SERVER "127.0.0.1"
#define NUM_NS (MEMP_NUM_NETCONN) //maximum number of node and seed, same as NUM_SOCKETS
#define ETH_MAX_MTU 1500
#define INVALID_CON_ID (-1)
#define RECV_SELECT_TIMEOUT_SEC (0)
#define RECV_SELECT_TIMEOUT_USEC (20000) //20ms
typedef struct ns
{
int con_id;
int sockfd;
s8_t role;
int protocol;
u32_t addr;
u16_t port;
u32_t local_addr;
u16_t local_port;
xTaskHandle handletask;
struct ns* next;
struct ns* nextseed;
#if (ATCMD_VER == ATVER_2) && ATCMD_SUPPORT_SSL
void *context;
#endif
} node;
extern xTaskHandle atcmd_lwip_tt_task;
extern _sema atcmd_lwip_tt_sema;
extern volatile int atcmd_lwip_tt_datasize;
extern volatile int atcmd_lwip_tt_lasttickcnt;
#define ATCMD_LWIP_TT_MAX_DELAY_TIME_MS (20) //transparent transmission interval
extern int atcmd_lwip_is_tt_mode(void);
extern void atcmd_lwip_set_tt_mode(int enable);
int atcmd_lwip_send_data(node *curnode, u8 *data, u16 data_sz, struct sockaddr_in cli_addr);
int atcmd_lwip_receive_data(node *curnode, u8 *buffer, u16 buffer_size, int *recv_size,
u8_t *udp_clientaddr, u16_t *udp_clientport);
node* create_node(int mode, s8_t role);
void init_node_pool(void);
void delete_node(node *n);
int hang_node(node* insert_node);
int hang_seednode(node* main_node ,node* insert_node);
node *seek_node(int con_id);
node *tryget_node(int n);
#endif
#endif //#ifndef __ATCMD_LWIP_H__

View File

@@ -0,0 +1,260 @@
#include <platform_stdlib.h>
#include <platform_opts.h>
#include <gpio_api.h>
#include <analogout_api.h>
#include <analogin_api.h>
#include "log_service.h"
#include "atcmd_mp.h"
#if CONFIG_ATCMD_MP_EXT0
extern void fATM0(void *arg); // MP ext0 AT command
#endif
#if CONFIG_ATCMD_MP_EXT1
extern void fATM1(void *arg); // MP ext1 AT command
#endif
#if CONFIG_ATCMD_MP
//-------- AT MP commands ---------------------------------------------------------------
void fATMG(void *arg)
{
gpio_t gpio_test;
int argc = 0, val, cnts, i, write=0, data=0;
char *argv[MAX_ARGC] = {0}, port, num;
PinName pin = NC;
u32 tConfigDebugInfo = ConfigDebugInfo;
AT_DBG_MSG(AT_FLAG_GPIO, AT_DBG_ALWAYS, "[ATMG]: _AT_MP_GPIO_TEST_");
if(!arg){
AT_DBG_MSG(AT_FLAG_GPIO, AT_DBG_ALWAYS, "[ATMG] Usage: ATMG=w,PINNAMES(ex:A0B1C2...),VALUE(0/1)");
AT_DBG_MSG(AT_FLAG_GPIO, AT_DBG_ALWAYS, "[ATMG] Usage: ATMG=r,PINNAMES(ex:A0B1C2...)");
return;
}
argc = parse_param(arg, argv);
cnts = strlen(argv[2]);
if(cnts % 2) return;
cnts /= 2;
if(cnts == 0) return;
if(strcmp(argv[1], "w") == 0){
write = 1;
if(strcmp(argv[3], "1") == 0)
data = 1;
}
// Remove debug info massage
_AT_DBG_MSG(AT_FLAG_GPIO, AT_DBG_ALWAYS, "[ATMG] %s: ", argv[1]);
ConfigDebugInfo = 0;
for(i=0; i<(cnts*2); i+=2){
pin = NC;
port = argv[2][i];
num = argv[2][i+1];
if(port >= 'a' && port <= 'z')
port -= ('a' - 'A');
if(num >= 'a' && num <= 'z')
num -= ('a' - 'A');
switch(port){
case 'A':
switch(num){
case '0': pin = PA_0; break; case '1': pin = PA_1; break; case '2': pin = PA_2; break; case '3': pin = PA_3; break;
case '4': pin = PA_4; break; case '5': pin = PA_5; break; case '6': pin = PA_6; break; case '7': pin = PA_7; break;
}
break;
case 'B':
switch(num){
case '0': pin = PB_0; break; case '1': pin = PB_1; break; case '2': pin = PB_2; break; case '3': pin = PB_3; break;
case '4': pin = PB_4; break; case '5': pin = PB_5; break; case '6': pin = PB_6; break; case '7': pin = PB_7; break;
}
break;
case 'C':
switch(num){
case '0': pin = PC_0; break; case '1': pin = PC_1; break; case '2': pin = PC_2; break; case '3': pin = PC_3; break;
case '4': pin = PC_4; break; case '5': pin = PC_5; break; case '6': pin = PC_6; break; case '7': pin = PC_7; break;
case '8': pin = PC_8; break; case '9': pin = PC_9; break;
}
break;
case 'D':
switch(num){
case '0': pin = PD_0; break; case '1': pin = PD_1; break; case '2': pin = PD_2; break; case '3': pin = PD_3; break;
case '4': pin = PD_4; break; case '5': pin = PD_5; break; case '6': pin = PD_6; break; case '7': pin = PD_7; break;
case '8': pin = PD_8; break; case '9': pin = PD_9; break;
}
break;
case 'E':
switch(num){
case '0': pin = PE_0; break; case '1': pin = PE_1; break; case '2': pin = PE_2; break; case '3': pin = PE_3; break;
case '4': pin = PE_4; break; case '5': pin = PE_5; break; case '6': pin = PE_6; break; case '7': pin = PE_7; break;
case '8': pin = PE_8; break; case '9': pin = PE_9; break; case 'A': pin = PE_A; break;
}
break;
case 'F':
switch(num){
case '0': pin = PF_0; break; case '1': pin = PF_1; break; case '2': pin = PF_2; break; case '3': pin = PF_3; break;
case '4': pin = PF_4; break; case '5': pin = PF_5; break;
}
break;
case 'G':
switch(num){
case '0': pin = PG_0; break; case '1': pin = PG_1; break; case '2': pin = PG_2; break; case '3': pin = PG_3; break;
case '4': pin = PG_4; break; case '5': pin = PG_5; break; case '6': pin = PG_6; break; case '7': pin = PG_7; break;
}
break;
case 'H':
switch(num){
case '0': pin = PH_0; break; case '1': pin = PH_1; break; case '2': pin = PH_2; break; case '3': pin = PH_3; break;
case '4': pin = PH_4; break; case '5': pin = PH_5; break; case '6': pin = PH_6; break; case '7': pin = PH_7; break;
}
break;
case 'I':
switch(num){
case '0': pin = PI_0; break; case '1': pin = PI_1; break; case '2': pin = PI_2; break; case '3': pin = PI_3; break;
case '4': pin = PI_4; break; case '5': pin = PI_5; break; case '6': pin = PI_6; break; case '7': pin = PI_7; break;
}
break;
case 'J':
switch(num){
case '0': pin = PJ_0; break; case '1': pin = PJ_1; break; case '2': pin = PJ_2; break; case '3': pin = PJ_3; break;
case '4': pin = PJ_4; break; case '5': pin = PJ_5; break; case '6': pin = PJ_6; break;
}
break;
case 'K':
switch(num){
case '0': pin = PK_0; break; case '1': pin = PK_1; break; case '2': pin = PK_2; break; case '3': pin = PK_3; break;
case '4': pin = PK_4; break; case '5': pin = PK_5; break; case '6': pin = PK_6; break;
}
break;
}
if(pin == NC){
_AT_DBG_MSG(AT_FLAG_GPIO, AT_DBG_ALWAYS, "X,");
continue;
}
// Initial input control pin
gpio_init(&gpio_test, pin);
if(write){
gpio_dir(&gpio_test, PIN_OUTPUT); // Direction: Output
gpio_mode(&gpio_test, PullNone); // No pull
gpio_write(&gpio_test, data);
_AT_DBG_MSG(AT_FLAG_GPIO, AT_DBG_ALWAYS, "%d,", data);
}else{
gpio_dir(&gpio_test, PIN_INPUT); // Direction: Input
gpio_mode(&gpio_test, PullUp); // Pull-High
val = gpio_read(&gpio_test);
_AT_DBG_MSG(AT_FLAG_GPIO, AT_DBG_ALWAYS, "%d,", val);
}
}
_AT_DBG_MSG(AT_FLAG_GPIO, AT_DBG_ALWAYS, "\n");
// Recover debug info massage
ConfigDebugInfo = tConfigDebugInfo;
}
void fATMR(void *arg)
{
u32 idx;
AT_PRINTK("[ATMR]: _AT_MP_SDR_TEST_");
#ifdef CONFIG_SDR_EN
for (idx = 0; idx < 0x200000; idx = idx+4){
HAL_WRITE32(0x30000000, idx, 0x12345678);
if (HAL_READ32(0x30000000, idx) != 0x12345678) {
AT_PRINTK("[ATMR]: SDR test fail addr 0x08x, value 0x08%x",(0x30000000+idx),HAL_READ32(0x30000000, idx));
return;
}
}
AT_PRINTK("[ATMR]: SDR test success");
#endif
}
void fATMD(void *arg)
{
int argc = 0;
char *argv[MAX_ARGC] = {0}, *ptmp;;
u16 vdac;
dac_t dac0;
argc = parse_param(arg, argv);
#if CONFIG_BT
analogout_init(&dac0, DA_0);
#endif
HalDelayUs(50*1000); // delay 50 ms for DAC_CAP 10uF
vdac = strtoul(argv[1], &ptmp, 16);
// 0x800(0v) ~ 0x000(1.65v) ~ 0x7ff(3.3v)
#if CONFIG_BT
analogout_write_u16(&dac0, vdac);
#endif
AT_PRINTK("[ATMD]: DAC = 0x%x", vdac);
}
#define AD2MV(ad,offset,gain) ((ad-offset)*1000/gain)
void fATMA(void *arg)
{
int argc = 0, channel;
char *argv[MAX_ARGC] = {0}, *ptmp;
u16 offset, gain, vadc, mv;
analogin_t adc;
argc = parse_param(arg, argv);
channel = atoi(argv[1]);
if(channel >= 1 && channel <= 3){
if(channel == 1)
analogin_init(&adc, AD_1);
else if(channel == 2)
analogin_init(&adc, AD_2);
else
analogin_init(&adc, AD_3);
vadc = (analogin_read_u16(&adc)>>4);
analogin_deinit(&adc);
sys_adc_calibration(0, &offset, &gain);
if((offset != 0xFFFF) && (gain != 0xFFFF)){
if(vadc < offset){
mv = 0;
}else{
mv = AD2MV(vadc, offset, gain);
}
AT_PRINTK("[ATMA]: ADC%d:0x%x = %d mv", channel, vadc, mv);
}else{
AT_PRINTK("[ATMA]: ADC%d:0x%x", channel, vadc);
}
}
}
void fATMt(void *arg)
{
int argc = 0;
char *argv[MAX_ARGC] = {0};
AT_PRINTK("[ATM#]: _AT_MP_TEST_");
argc = parse_param(arg, argv);
}
void fATMx(void *arg)
{
AT_PRINTK("[ATM?]: _AT_MP_HELP_");
}
log_item_t at_mp_items[] = {
{"ATMG", fATMG,}, // MP GPIO test
{"ATMR", fATMR,}, // MP SDR test
{"ATMD", fATMD,}, // MP DAC
{"ATMA", fATMA,}, // MP ADC
{"ATM#", fATMt,}, // test command
{"ATM?", fATMx,}, // Help
#if CONFIG_ATCMD_MP_EXT0
{"ATM0", fATM0,}, // MP ext0 AT command
#endif
#if CONFIG_ATCMD_MP_EXT1
{"ATM1", fATM1,}, // MP ext1 AT command
#endif
};
void at_mp_init(void)
{
log_service_add_table(at_mp_items, sizeof(at_mp_items)/sizeof(at_mp_items[0]));
}
#if SUPPORT_LOG_SERVICE
log_module_init(at_mp_init);
#endif
#endif // #if CONFIG_ATCMD_MP

View File

@@ -0,0 +1,19 @@
#ifndef __ATCMD_MP_H__
#define __ATCMD_MP_H__
#include <platform_opts.h>
#if CONFIG_BT
#define CONFIG_ATCMD_MP_EXT0 1 //support MP ext0 AT command
#else
#define CONFIG_ATCMD_MP_EXT0 0 //support MP ext0 AT command
#endif
#define CONFIG_ATCMD_MP_EXT1 0 //support MP ext1 AT command
typedef struct _at_command_mp_ext_item_{
char *mp_ext_cmd;
int (*mp_ext_fun)(void **argv, int argc);
char *mp_ext_usage;
}at_mp_ext_item_t;
#endif

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,5 @@
#ifndef __ATCMD_SYS_H__
#define __ATCMD_SYS_H__
#endif

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,161 @@
#ifndef __ATCMD_WIFI_H__
#define __ATCMD_WIFI_H__
#include "main.h"
#include "lwip_netconf.h"
#ifndef WLAN0_NAME
#define WLAN0_NAME "wlan0"
#endif
#ifndef WLAN1_NAME
#define WLAN1_NAME "wlan1"
#endif
/* Give default value if not defined */
#ifndef NET_IF_NUM
#ifdef CONFIG_CONCURRENT_MODE
#define NET_IF_NUM ((CONFIG_ETHERNET) + (CONFIG_WLAN) + 1)
#else
#define NET_IF_NUM ((CONFIG_ETHERNET) + (CONFIG_WLAN))
#endif // end of CONFIG_CONCURRENT_MODE
#endif // end of NET_IF_NUM
/*Static IP ADDRESS*/
#ifndef IP_ADDR0
#define IP_ADDR0 192
#define IP_ADDR1 168
#define IP_ADDR2 1
#define IP_ADDR3 80
#endif
/*NETMASK*/
#ifndef NETMASK_ADDR0
#define NETMASK_ADDR0 255
#define NETMASK_ADDR1 255
#define NETMASK_ADDR2 255
#define NETMASK_ADDR3 0
#endif
/*Gateway Address*/
#ifndef GW_ADDR0
#define GW_ADDR0 192
#define GW_ADDR1 168
#define GW_ADDR2 1
#define GW_ADDR3 1
#endif
/*Static IP ADDRESS*/
#ifndef AP_IP_ADDR0
#define AP_IP_ADDR0 192
#define AP_IP_ADDR1 168
#define AP_IP_ADDR2 43
#define AP_IP_ADDR3 1
#endif
/*NETMASK*/
#ifndef AP_NETMASK_ADDR0
#define AP_NETMASK_ADDR0 255
#define AP_NETMASK_ADDR1 255
#define AP_NETMASK_ADDR2 255
#define AP_NETMASK_ADDR3 0
#endif
/*Gateway Address*/
#ifndef AP_GW_ADDR0
#define AP_GW_ADDR0 192
#define AP_GW_ADDR1 168
#define AP_GW_ADDR2 43
#define AP_GW_ADDR3 1
#endif
#if CONFIG_EXAMPLE_UART_ATCMD
#include "wifi_structures.h"
#include <wlan_fast_connect/example_wlan_fast_connect.h>
typedef struct _UART_LOG_CONF_{
u32 BaudRate;
u8 DataBits;
u8 StopBits;
u8 Parity;
u8 FlowControl;
}UART_LOG_CONF, *PUART_LOG_CONF;
#define ATCMD_WIFI_CONN_STORE_MAX_NUM (1)
struct atcmd_wifi_conf{
int32_t auto_enable;
rtw_wifi_setting_t setting;
int32_t reconn_num;
int32_t reconn_last_index;
struct wlan_fast_reconnect reconn[ATCMD_WIFI_CONN_STORE_MAX_NUM];
};
#define ATCMD_LWIP_CONN_STORE_MAX_NUM (1)
struct atcmd_lwip_conn_info{
int32_t role; //client, server or seed
uint32_t protocol; //tcp or udp
uint32_t remote_addr; //remote ip
uint32_t remote_port; //remote port
uint32_t local_addr; //locale ip, not used yet
uint32_t local_port; //locale port, not used yet
uint32_t reserved; //reserve for further use
};
struct atcmd_lwip_conf {
int32_t enable; //enable or not
int32_t conn_num;
int32_t last_index;
int32_t reserved; //reserve for further use
struct atcmd_lwip_conn_info conn[ATCMD_LWIP_CONN_STORE_MAX_NUM];
};
typedef enum {
AT_PARTITION_ALL = 0,
AT_PARTITION_UART = 1,
AT_PARTITION_WIFI = 2,
AT_PARTITION_LWIP = 3
} AT_PARTITION;
typedef enum {
AT_PARTITION_READ = 0,
AT_PARTITION_WRITE = 1,
AT_PARTITION_ERASE = 2
} AT_PARTITION_OP;
//first segment for uart
#define UART_SETTING_BACKUP_SECTOR (0x8000)
#define UART_CONF_DATA_OFFSET (0)
#define UART_CONF_DATA_SIZE ((((sizeof(UART_LOG_CONF)-1)>>2) + 1)<<2)
//second segment for wifi config
#define WIFI_CONF_DATA_OFFSET (UART_CONF_DATA_OFFSET+UART_CONF_DATA_SIZE)
#define WIFI_CONF_DATA_SIZE ((((sizeof(struct atcmd_wifi_conf)-1)>>2) + 1)<<2)
//fouth segment for lwip config
#define LWIP_CONF_DATA_OFFSET (WIFI_CONF_DATA_OFFSET+WIFI_CONF_DATA_SIZE)
#define LWIP_CONF_DATA_SIZE ((((sizeof(struct atcmd_lwip_conf)-1)>>2) + 1)<<2)
extern void atcmd_update_partition_info(AT_PARTITION id, AT_PARTITION_OP ops, u8 *data, u16 len);
#define ATSTRING_LEN (LOG_SERVICE_BUFLEN)
extern char at_string[ATSTRING_LEN];
extern unsigned char gAT_Echo; // default echo on
//extern void uart_at_lock(void);
//extern void uart_at_unlock(void);
extern void uart_at_send_string(char *str);
extern void uart_at_send_buf(u8 *buf, u32 len);
#define at_printf(fmt, args...) do{\
/*uart_at_lock();*/\
snprintf(at_string, ATSTRING_LEN, fmt, ##args); \
uart_at_send_string(at_string);\
/*uart_at_unlock();*/\
}while(0)
#define at_print_data(data, size) do{\
/*uart_at_lock();*/\
uart_at_send_buf(data, size);\
/*uart_at_unlock();*/\
}while(0)
#else
#define at_printf(fmt, args...) do{printf(fmt, ##args);}while(0)
#define at_print_data(data, size) do{__rtl_memDump(data, size, NULL);}while(0)
#endif//#if CONFIG_EXAMPLE_UART_ATCMD
#endif

View File

@@ -0,0 +1,497 @@
#include <stdarg.h>
#include <string.h>
#include <stdio.h>
#include "FreeRTOS.h"
#if defined(configUSE_WAKELOCK_PMU) && (configUSE_WAKELOCK_PMU == 1)
#include "freertos_pmu.h"
#endif
#include "log_service.h"
#include "task.h"
#include "semphr.h"
#include "main.h"
//#include "wifi_util.h"
#include "atcmd_wifi.h"
#if CONFIG_EXAMPLE_UART_ATCMD || CONFIG_EXAMPLE_SPI_ATCMD
#include "atcmd_lwip.h"
#endif
#if SUPPORT_LOG_SERVICE
//======================================================
struct list_head log_hash[ATC_INDEX_NUM];
extern void at_wifi_init(void);
extern void at_fs_init(void);
extern void at_sys_init(void);
extern void at_ethernet_init(void);
extern void at_google_init(void);
extern void at_transport_init(void);
//extern void at_app_init(void);
extern void at_mp_init(void);
extern void at_bt_init(void);
#if (CONFIG_JOYLINK || CONFIG_GAGENT || CONFIG_QQ_LINK || \
CONFIG_AIRKISS_CLOUD || CONFIG_ALINK || CONFIG_HILINK || CONFIG_GREE || \
(defined(CONFIG_RIC) && CONFIG_RIC))
extern void at_cloud_init(void);
#endif
void at_log_init(void);
char log_buf[LOG_SERVICE_BUFLEN];
#if CONFIG_LOG_HISTORY
char log_history[LOG_HISTORY_LEN][LOG_SERVICE_BUFLEN];
static unsigned int log_history_count = 0;
#endif
xSemaphoreHandle log_rx_interrupt_sema = NULL;
#if CONFIG_LOG_SERVICE_LOCK
xSemaphoreHandle log_service_sema = NULL;
#endif
extern xSemaphoreHandle uart_rx_interrupt_sema;
#if CONFIG_INIC_EN
extern unsigned char inic_cmd_ioctl;
#endif
//#if defined (__ICCARM__)
//#pragma section=".data.log_init"
//
//unsigned int __log_init_begin__;
//unsigned int __log_init_end__;
//#elif defined ( __CC_ARM ) || defined(__GNUC__)
#if defined (__ICCARM__) || defined ( __CC_ARM ) || defined(__GNUC__)
//#pragma section=".data.log_init"
log_init_t* __log_init_begin__;
log_init_t* __log_init_end__;
log_init_t log_init_table[] = {
at_wifi_init,
// at_fs_init,
at_sys_init,
at_log_init,
// at_app_init,
#if CONFIG_ETHERNET
at_ethernet_init,
#endif
#if CONFIG_GOOGLE_NEST
at_google_init,
#endif
#if CONFIG_TRANSPORT
at_transport_init,
#endif
#if CONFIG_ATCMD_MP
at_mp_init,
#endif
#if CONFIG_BT
at_bt_init,
#endif
#if (CONFIG_JOYLINK || CONFIG_GAGENT || CONFIG_QQ_LINK || \
CONFIG_AIRKISS_CLOUD || CONFIG_ALINK || CONFIG_HILINK || CONFIG_GREE || \
(defined(CONFIG_RIC) && CONFIG_RIC))
at_cloud_init,
#endif
};
#else
#error "not implement, add to linker script"
extern unsigned int __log_init_begin__;
extern unsigned int __log_init_end__;
#endif
#if defined(__GNUC__)
#define USE_STRSEP
#endif
//======================================================
int hash_index(char *str)
{
unsigned int seed = 131; // 31 131 1313 13131 131313 etc..
unsigned int hash = 0;
while (*str)
{
hash = hash * seed + (*str++);
}
return (hash & 0x7FFFFFFF);
}
void log_add_new_command(log_item_t *new)
{
int index = hash_index(new->log_cmd)%ATC_INDEX_NUM;
list_add(&new->node, &log_hash[index]);
}
void start_log_service(void);
void log_service_init(void)
{
int i;
//#if defined (__ICCARM__)
// log_init_t *log_init_table;
// __log_init_begin__ = (unsigned int)__section_begin(".data.log_init");
// __log_init_end__ = (unsigned int)__section_end(".data.log_init");
// log_init_table = (log_init_t *)__log_init_begin__;
//#elif defined(__CC_ARM) || defined(__GNUC__)
#if defined (__ICCARM__) || defined(__CC_ARM) || defined(__GNUC__)
__log_init_begin__ = log_init_table;
__log_init_end__ = __log_init_begin__ + sizeof(log_init_table);
#else
#error "not implement"
#endif
for(i=0;i<ATC_INDEX_NUM;i++)
INIT_LIST_HEAD(&log_hash[i]);
for(i=0;i<(__log_init_end__-__log_init_begin__)/sizeof(log_init_t); i++)
log_init_table[i]();
/* Initial uart rx swmaphore*/
vSemaphoreCreateBinary(log_rx_interrupt_sema);
xSemaphoreTake(log_rx_interrupt_sema, 1/portTICK_RATE_MS);
#if CONFIG_LOG_SERVICE_LOCK
log_service_lock_init();
#endif
start_log_service();
}
//sizeof(log_items)/sizeof(log_items[0])
void log_service_add_table(log_item_t *tbl, int len)
{
int i;
for(i=0;i<len;i++)
log_add_new_command(&tbl[i]);
}
void* log_action(char *cmd)
{
int search_cnt=0;
int index = hash_index(cmd)%ATC_INDEX_NUM;
struct list_head *head = &log_hash[index];
struct list_head *iterator;
log_item_t *item;
void *act = NULL;
list_for_each(iterator, head) {
item = list_entry(iterator, log_item_t, node);
search_cnt++;
if( strcmp(item->log_cmd, cmd) == 0){
//printf("%s match %s, search cnt %d\n\r", cmd, item->log_cmd, search_cnt);
act = (void*)item->at_act;
break;
}
}
return act;
}
void* log_handler(char *cmd)
{
log_act_t action=NULL;
char buf[LOG_SERVICE_BUFLEN];
memset(buf, 0, LOG_SERVICE_BUFLEN);
char *copy=buf;
char *token = NULL;
char *param = NULL;
char tok[5] = {0};//'\0'
#if CONFIG_LOG_HISTORY
strcpy(log_history[((log_history_count++)%LOG_HISTORY_LEN)], log_buf);
#endif
strncpy(copy, cmd,LOG_SERVICE_BUFLEN-1);
#if defined(USE_STRSEP)
token = _strsep(&copy, "=");
param = copy;
#else
token = strtok(copy, "=");
param = strtok(NULL, NULL);
#endif
if(token && (strlen(token) <= 4))
strcpy(tok, token);
else{
//printf("\n\rAT Cmd format error!\n");
return NULL;
};
//printf(" Command %s \n\r ", tok);
//printf(" Param %s \n\r", param);
action = (log_act_t)log_action(tok);
if(action){
action(param);
}
return (void*)action;
}
int parse_param(char *buf, char **argv)
{
int argc = 1;
char str_buf[LOG_SERVICE_BUFLEN];
memset(str_buf, 0, LOG_SERVICE_BUFLEN);
int str_count = 0;
int buf_cnt = 0;
if(buf == NULL)
goto exit;
while((argc < MAX_ARGC) && (*buf != '\0')) {
while((*buf == ',') || (*buf == '[') || (*buf == ']')){
if((*buf == ',') && (*(buf+1) == ',')){
argv[argc] = NULL;
argc++;
}
*buf = '\0';
buf++;
}
if(*buf == '\0')
break;
else if(*buf == '"'){
memset(str_buf,'\0',LOG_SERVICE_BUFLEN);
str_count = 0;
buf_cnt = 0;
*buf = '\0';
buf ++;
if(*buf == '\0')
break;
argv[argc] = buf;
while((*buf != '"')&&(*buf != '\0')){
if(*buf == '\\'){
buf ++;
buf_cnt++;
}
str_buf[str_count] = *buf;
str_count++;
buf_cnt++;
buf ++;
}
*buf = '\0';
memcpy(buf-buf_cnt,str_buf,buf_cnt);
}
else{
argv[argc] = buf;
}
argc++;
buf++;
while( (*buf != ',')&&(*buf != '\0')&&(*buf != '[')&&(*buf != ']') )
buf++;
}
exit:
return argc;
}
unsigned char gDbgLevel = AT_DBG_ERROR;
unsigned int gDbgFlag = 0xFFFFFFFF;
void at_set_debug_level(unsigned char newDbgLevel)
{
gDbgLevel = newDbgLevel;
}
void at_set_debug_mask(unsigned int newDbgFlag)
{
gDbgFlag = newDbgFlag;
}
#if SUPPORT_INTERACTIVE_MODE
extern char uart_buf[64];
void legency_interactive_handler(unsigned char argc, unsigned char **argv)
{
#if 0 //defined(CONFIG_PLATFORM_8195A)
if(argc<1)
{
DiagPrintf("Wrong argument number!\r\n");
return;
}
DiagPrintf("Wlan Normal Mode\n");
WlanNormal( argc, argv);
#else
strncpy(uart_buf, log_buf, 63);//uart_buf[64]
xSemaphoreGive(uart_rx_interrupt_sema);
#endif
}
#endif
#if CONFIG_WLAN
#ifndef WLAN0_NAME
#define WLAN0_NAME "wlan0"
#endif
#ifndef WLAN1_NAME
#define WLAN1_NAME "wlan1"
#endif
int mp_commnad_handler(char *cmd)
{
char buf[64];
char *token = NULL;
memset(buf, 0, 64);
//strcpy(buf, cmd);
strncpy(buf, cmd, (64-1));
token = strtok(buf, " ");
if(token && (strcmp(buf, "iwpriv") == 0)){
token = strtok(NULL, "");
wext_private_command(WLAN0_NAME, token, 1);
return 0;
}
return -1;
}
#endif
void print_help_msg(void){
#if CONFIG_WLAN
extern void print_wlan_help(void);
print_wlan_help();
#endif
//add other help message print here
}
int print_help_handler(char *cmd){
if(strcmp(cmd, "help") == 0){
print_help_msg();
return 0;
}
return -1;
}
#if CONFIG_LOG_SERVICE_LOCK
void log_service_lock(void)
{
rtw_down_sema(&log_service_sema);
}
u32 log_service_lock_timeout(u32 ms)
{
return rtw_down_timeout_sema(&log_service_sema, ms);
}
void log_service_unlock(void)
{
rtw_up_sema(&log_service_sema);
}
void log_service_lock_init(void){
rtw_init_sema(&log_service_sema, 1);
}
#endif
void log_service(void *param)
{
_AT_DBG_MSG(AT_FLAG_COMMON, AT_DBG_ALWAYS, "\n\rStart LOG SERVICE MODE\n\r");
_AT_DBG_MSG(AT_FLAG_COMMON, AT_DBG_ALWAYS, "\n\r# ");
while(1){
while(xSemaphoreTake(log_rx_interrupt_sema, portMAX_DELAY) != pdTRUE);
#if CONFIG_LOG_SERVICE_LOCK
log_service_lock();
#endif
if(log_handler((char *)log_buf) == NULL){
#if CONFIG_WLAN
if(mp_commnad_handler((char *)log_buf) < 0)
#endif
{
#if SUPPORT_INTERACTIVE_MODE
print_help_handler((char *)log_buf);
legency_interactive_handler(NULL, NULL);
#else
if(print_help_handler((char *)log_buf) < 0){
at_printf("\r\nunknown command '%s'", log_buf);
}
#endif
}
}
log_buf[0] = '\0';
#if CONFIG_INIC_EN
inic_cmd_ioctl = 0;
#endif
_AT_DBG_MSG(AT_FLAG_COMMON, AT_DBG_ALWAYS, "\n\r[MEM] After do cmd, available heap %d\n\r", xPortGetFreeHeapSize());
_AT_DBG_MSG(AT_FLAG_COMMON, AT_DBG_ALWAYS, "\r\n\n# "); //"#" is needed for mp tool
#if CONFIG_EXAMPLE_UART_ATCMD
if(atcmd_lwip_is_tt_mode())
at_printf(STR_END_OF_ATDATA_RET);
else
at_printf(STR_END_OF_ATCMD_RET);
#endif
#if CONFIG_LOG_SERVICE_LOCK
log_service_unlock();
#endif
#if defined(configUSE_WAKELOCK_PMU) && (configUSE_WAKELOCK_PMU == 1)
pmu_release_wakelock(BIT(PMU_LOGUART_DEVICE));
#endif
}
}
#define STACKSIZE 1280
void start_log_service(void)
{
xTaskHandle CreatedTask;
int result;
#if CONFIG_USE_TCM_HEAP
/*********************************************************************
*
* ATCMD V2 supports commands for SSL
* It will cause problems while doing SSL operations if the stack is placed in TCM region
*
*********************************************************************/
void *stack_addr = NULL;
#if (ATCMD_VER == ATVER_1) || ((ATCMD_VER == ATVER_2)&&(ATCMD_SUPPORT_SSL == 0))
extern void *tcm_heap_malloc(int size);
stack_addr = tcm_heap_malloc(STACKSIZE * sizeof(int));
if(stack_addr == NULL){
}
#endif
result = xTaskGenericCreate(
log_service,
( signed portCHAR * ) "log_service",
STACKSIZE,
NULL,
tskIDLE_PRIORITY + 5,
&CreatedTask,
stack_addr,
NULL);
#else
result = xTaskCreate( log_service, ( signed portCHAR * ) "log_service", STACKSIZE, NULL, tskIDLE_PRIORITY + 5, &CreatedTask );
#endif
if(result != pdPASS) {
printf("\n\r%s xTaskCreate failed", __FUNCTION__);
}
}
void fAT_exit(void *arg){
printf("\n\rLeave LOG SERVICE");
vTaskDelete(NULL);
}
#if CONFIG_LOG_HISTORY
void fAT_log(void *arg){
int i = 0;
printf("[AT]log history:\n\n\r");
if(log_history_count > LOG_HISTORY_LEN){
for(i=0; i<4; i++)
printf(" %s\n\r", log_history[((log_history_count+i)%LOG_HISTORY_LEN)]);
}
else{
for(i=0; i<(log_history_count-1); i++)
printf(" %s\n\r", log_history[i]);
}
}
#endif
log_item_t at_log_items[ ] = {
{"AT--", fAT_exit,},
#if CONFIG_LOG_HISTORY
{"AT??", fAT_log,},
#endif
{"ATxx", fAT_exit,}
};
void at_log_init(void)
{
log_service_add_table(at_log_items, sizeof(at_log_items)/sizeof(at_log_items[0]));
}
log_module_init(at_log_init);
#endif

View File

@@ -0,0 +1,127 @@
#ifndef LOG_SERVICE_H
#define LOG_SERVICE_H
#include "dlist.h"
/*
* Include user defined options first. Anything not defined in these files
* will be set to standard values. Override anything you dont like!
*/
#if defined(CONFIG_PLATFORM_8195A) || defined(CONFIG_PLATFORM_8711B)
#include "platform_opts.h"
#include "platform_stdlib.h"
#endif
//#ifdef __ICCARM__
//#define STRINGIFY(s) #s
//#define SECTION(_name) _Pragma( STRINGIFY(location=_name))
//#define log_module_init(fn) \
// SECTION(".data.log_init") __root static void* log_##fn = (void*)fn
//#elif defined(__CC_ARM)
//#define log_module_init(fn) \
//static void* log_##fn __attribute__((section(".data.log_init"))) = (void*)fn;
//#define DiagPrintf printf
//#elif defined(__GNUC__)
//#define log_module_init(fn) \
//static void* log_##fn __attribute__((section(".data.log_init"))) = (void*)fn;
//#else
//#error "not implement"
//#endif
#define log_module_init(fn)
#define ATC_INDEX_NUM 32
#ifndef SUPPORT_LOG_SERVICE
#define SUPPORT_LOG_SERVICE 1
#endif
//LOG_SERVICE_BUFLEN: default, only 63 bytes could be used for keeping input
// cmd, the last byte is for string end ('\0').
#ifndef LOG_SERVICE_BUFLEN
#define LOG_SERVICE_BUFLEN 64
#endif
#ifndef CONFIG_LOG_HISTORY
#define CONFIG_LOG_HISTORY 0
#if CONFIG_LOG_HISTORY
#define LOG_HISTORY_LEN 5
#endif
#endif //#ifndef CONFIG_LOG_HISTORY
#ifndef MAX_ARGC
#define MAX_ARGC 12
#endif
#ifndef CONFIG_LOG_SERVICE_LOCK
#define CONFIG_LOG_SERVICE_LOCK 0 // //to protect log_buf[], only one command processed per time
#endif
#define AT_BIT(n) (1<<n)
#define AT_FLAG_DUMP AT_BIT(0)
#define AT_FLAG_EDIT AT_BIT(1)
#define AT_FLAG_ADC AT_BIT(2)
#define AT_FLAG_GPIO AT_BIT(3)
#define AT_FLAG_OTA AT_BIT(4)
#define AT_FLAG_NFC AT_BIT(5)
#define AT_FLAG_OS AT_BIT(6)
#define AT_FLAG_LWIP AT_BIT(7)
#define AT_FLAG_COMMON AT_BIT(8)
#define AT_FLAG_WIFI AT_BIT(9)
#define AT_FLAG_RDP AT_BIT(10)
enum{
AT_DBG_OFF = 0,
AT_DBG_ALWAYS,
AT_DBG_ERROR,
AT_DBG_WARNING,
AT_DBG_INFO
};
extern unsigned char gDbgLevel;
extern unsigned int gDbgFlag;
#define AT_PRINTK(...) \
do{ \
printf(__VA_ARGS__); \
printf("\r\n"); \
}while(0)
#define _AT_PRINTK(...) printf(__VA_ARGS__)
#define AT_DBG_MSG(flag, level, ...) \
do{ \
if(((flag) & gDbgFlag) && (level <= gDbgLevel)){ \
AT_PRINTK(__VA_ARGS__); \
} \
}while(0)
#define _AT_DBG_MSG(flag, level, ...) \
do{ \
if(((flag) & gDbgFlag) && (level <= gDbgLevel)){ \
_AT_PRINTK(__VA_ARGS__); \
} \
}while(0)
#ifndef SUPPORT_INTERACTIVE_MODE
#define SUPPORT_INTERACTIVE_MODE 0
#endif //#ifndef SUPPORT_INTERACTIVE_MODE
typedef void (*log_init_t)(void);
typedef void (*log_act_t)(void*);
typedef struct _at_command_item_{
char *log_cmd;
log_act_t at_act;
struct list_head node;
}log_item_t;
void log_service_add_table(log_item_t *tbl, int len);
int parse_param(char *buf, char **argv);
#if CONFIG_LOG_SERVICE_LOCK
void log_service_lock_init(void);
void log_service_lock(void);
u32 log_service_lock_timeout(u32 ms);
void log_service_unlock(void);
#endif
#define C_NUM_AT_CMD 4 //"ATxx", 4 characters
#define C_NUM_AT_CMD_DLT 1 //"=", 1 charater
#define STR_END_OF_ATCMD_RET "\r\n\n# " //each AT command response will end with this string
#define STR_END_OF_ATDATA_RET "\r\n\n> " //data transparent transmission indicator
#endif

View File

@@ -0,0 +1,669 @@
/* Includes ------------------------------------------------------------------*/
#include "lwip/mem.h"
#include "lwip/memp.h"
#include "lwip/dhcp.h"
#include "lwip/dns.h"
#include "ethernetif.h"
#include "main.h"
#include "lwip_netconf.h"
#ifdef LWIP_HOOK_TCP_ISN
#include "lwip/tcp.h"
#endif
#if CONFIG_WLAN
#include "wifi_ind.h"
#endif
#if defined(STM32F2XX)
#include "stm322xg_eval_lcd.h"
#elif defined(STM32F4XX)
#include "stm324xg_eval_lcd.h"
#endif
#include <platform/platform_stdlib.h>
#if defined(CONFIG_FAST_DHCP) && CONFIG_FAST_DHCP
#include "wlan_fast_connect/example_wlan_fast_connect.h"
#endif
/*Static IP ADDRESS*/
#ifndef IP_ADDR0
#define IP_ADDR0 192
#define IP_ADDR1 168
#define IP_ADDR2 1
#define IP_ADDR3 80
#endif
/*NETMASK*/
#ifndef NETMASK_ADDR0
#define NETMASK_ADDR0 255
#define NETMASK_ADDR1 255
#define NETMASK_ADDR2 255
#define NETMASK_ADDR3 0
#endif
/*Gateway Address*/
#ifndef GW_ADDR0
#define GW_ADDR0 192
#define GW_ADDR1 168
#define GW_ADDR2 1
#define GW_ADDR3 1
#endif
/*Static IP ADDRESS*/
#ifndef AP_IP_ADDR0
#define AP_IP_ADDR0 192
#define AP_IP_ADDR1 168
#define AP_IP_ADDR2 43
#define AP_IP_ADDR3 1
#endif
/*NETMASK*/
#ifndef AP_NETMASK_ADDR0
#define AP_NETMASK_ADDR0 255
#define AP_NETMASK_ADDR1 255
#define AP_NETMASK_ADDR2 255
#define AP_NETMASK_ADDR3 0
#endif
/*Gateway Address*/
#ifndef AP_GW_ADDR0
#define AP_GW_ADDR0 192
#define AP_GW_ADDR1 168
#define AP_GW_ADDR2 43
#define AP_GW_ADDR3 1
#endif
/*Static IP ADDRESS FOR ETHERNET*/
#ifndef ETH_IP_ADDR0
#define ETH_IP_ADDR0 192
#define ETH_IP_ADDR1 168
#define ETH_IP_ADDR2 0
#define ETH_IP_ADDR3 80
#endif
/*NETMASK FOR ETHERNET*/
#ifndef ETH_NETMASK_ADDR0
#define ETH_NETMASK_ADDR0 255
#define ETH_NETMASK_ADDR1 255
#define ETH_NETMASK_ADDR2 255
#define ETH_NETMASK_ADDR3 0
#endif
/*Gateway address for ethernet*/
#ifndef ETH_GW_ADDR0
#define ETH_GW_ADDR0 192
#define ETH_GW_ADDR1 168
#define ETH_GW_ADDR2 0
#define ETH_GW_ADDR3 1
#endif
/* Private define ------------------------------------------------------------*/
#define MAX_DHCP_TRIES 5
/* Private macro -------------------------------------------------------------*/
/* Private variables ---------------------------------------------------------*/
struct netif xnetif[NET_IF_NUM]; /* network interface structure */
/* Private functions ---------------------------------------------------------*/
/**
* @brief Initializes the lwIP stack
* @param None
* @retval None
*/
#if CONFIG_WLAN
extern int error_flag;
extern rtw_mode_t wifi_mode;
#endif
int lwip_init_done = 0;
void LwIP_Init(void)
{
struct ip_addr ipaddr;
struct ip_addr netmask;
struct ip_addr gw;
int8_t idx = 0;
/* Create tcp_ip stack thread */
tcpip_init( NULL, NULL );
/* - netif_add(struct netif *netif, struct ip_addr *ipaddr,
struct ip_addr *netmask, struct ip_addr *gw,
void *state, err_t (* init)(struct netif *netif),
err_t (* input)(struct pbuf *p, struct netif *netif))
Adds your network interface to the netif_list. Allocate a struct
netif and pass a pointer to this structure as the first argument.
Give pointers to cleared ip_addr structures when using DHCP,
or fill them with sane numbers otherwise. The state pointer may be NULL.
The init function pointer must point to a initialization function for
your ethernet netif interface. The following code illustrates it's use.*/
//printf("NET_IF_NUM:%d\n\r",NET_IF_NUM);
for(idx=0;idx<NET_IF_NUM;idx++){
#if LWIP_VERSION_MAJOR >= 2
if(idx==0){
IP4_ADDR(ip_2_ip4(&ipaddr), IP_ADDR0, IP_ADDR1, IP_ADDR2, IP_ADDR3);
IP4_ADDR(ip_2_ip4(&netmask), NETMASK_ADDR0, NETMASK_ADDR1 , NETMASK_ADDR2, NETMASK_ADDR3);
IP4_ADDR(ip_2_ip4(&gw), GW_ADDR0, GW_ADDR1, GW_ADDR2, GW_ADDR3);
}
else{
IP4_ADDR(ip_2_ip4(&ipaddr), AP_IP_ADDR0, AP_IP_ADDR1, AP_IP_ADDR2, AP_IP_ADDR3);
IP4_ADDR(ip_2_ip4(&netmask), AP_NETMASK_ADDR0, AP_NETMASK_ADDR1 , AP_NETMASK_ADDR2, AP_NETMASK_ADDR3);
IP4_ADDR(ip_2_ip4(&gw), AP_GW_ADDR0, AP_GW_ADDR1, AP_GW_ADDR2, AP_GW_ADDR3);
}
#else
if(idx==0){
IP4_ADDR(&ipaddr, IP_ADDR0, IP_ADDR1, IP_ADDR2, IP_ADDR3);
IP4_ADDR(&netmask, NETMASK_ADDR0, NETMASK_ADDR1 , NETMASK_ADDR2, NETMASK_ADDR3);
IP4_ADDR(&gw, GW_ADDR0, GW_ADDR1, GW_ADDR2, GW_ADDR3);
}
else{
IP4_ADDR(&ipaddr, AP_IP_ADDR0, AP_IP_ADDR1, AP_IP_ADDR2, AP_IP_ADDR3);
IP4_ADDR(&netmask, AP_NETMASK_ADDR0, AP_NETMASK_ADDR1 , AP_NETMASK_ADDR2, AP_NETMASK_ADDR3);
IP4_ADDR(&gw, AP_GW_ADDR0, AP_GW_ADDR1, AP_GW_ADDR2, AP_GW_ADDR3);
}
#endif
#if CONFIG_ETHERNET
if(idx == NET_IF_NUM - 1)
{
#if LWIP_VERSION_MAJOR >= 2
IP4_ADDR(ip_2_ip4(&ipaddr), ETH_IP_ADDR0, ETH_IP_ADDR1, ETH_IP_ADDR2, ETH_IP_ADDR3);
IP4_ADDR(ip_2_ip4(&netmask), ETH_NETMASK_ADDR0, ETH_NETMASK_ADDR1 , ETH_NETMASK_ADDR2, ETH_NETMASK_ADDR3);
IP4_ADDR(ip_2_ip4(&gw), ETH_GW_ADDR0, ETH_GW_ADDR1, ETH_GW_ADDR2, ETH_GW_ADDR3);
#else
IP4_ADDR(&ipaddr, ETH_IP_ADDR0, ETH_IP_ADDR1, ETH_IP_ADDR2, ETH_IP_ADDR3);
IP4_ADDR(&netmask, ETH_NETMASK_ADDR0, ETH_NETMASK_ADDR1 , ETH_NETMASK_ADDR2, ETH_NETMASK_ADDR3);
IP4_ADDR(&gw, ETH_GW_ADDR0, ETH_GW_ADDR1, ETH_GW_ADDR2, ETH_GW_ADDR3);
#endif
}
#endif
xnetif[idx].name[0] = 'r';
xnetif[idx].name[1] = '0'+idx;
#if LWIP_VERSION_MAJOR >= 2
#if CONFIG_ETHERNET
if(idx == NET_IF_NUM - 1)
netif_add(&xnetif[idx], ip_2_ip4(&ipaddr), ip_2_ip4(&netmask),ip_2_ip4(&gw), NULL, &ethernetif_mii_init, &tcpip_input);
else
netif_add(&xnetif[idx], ip_2_ip4(&ipaddr), ip_2_ip4(&netmask),ip_2_ip4(&gw), NULL, &ethernetif_init, &tcpip_input);
#else
netif_add(&xnetif[idx], ip_2_ip4(&ipaddr), ip_2_ip4(&netmask),ip_2_ip4(&gw), NULL, &ethernetif_init, &tcpip_input);
#endif
#else
#if CONFIG_ETHERNET
if(idx == NET_IF_NUM - 1)
netif_add(&xnetif[idx], &ipaddr, &netmask, &gw, NULL, &ethernetif_mii_init, &tcpip_input);
else
netif_add(&xnetif[idx], &ipaddr, &netmask, &gw, NULL, &ethernetif_init, &tcpip_input);
#else
netif_add(&xnetif[idx], &ipaddr, &netmask, &gw, NULL, &ethernetif_init, &tcpip_input);
#endif
#endif
printf("interface %d is initialized\n", idx);
}
/* Registers the default network interface. */
netif_set_default(&xnetif[0]);
/*move these operations to wifi_on/wifi_off*/
#if 0
/* When the netif is fully configured this function must be called.*/
for(idx = 0;idx < NET_IF_NUM;idx++)
netif_set_up(&xnetif[idx]);
#endif
lwip_init_done = 1;
}
#if defined(CONFIG_FAST_DHCP) && CONFIG_FAST_DHCP
extern write_reconnect_ptr p_write_reconnect_ptr;
extern uint32_t offer_ip;
extern uint32_t server_ip;
extern u8 is_the_same_ap;
#endif
#if defined(CONFIG_CONCURRENT_MODE) && defined(CONFIG_STA_STA_MODE)
#undef IP_ADDR2
#undef GW_ADDR2
static u8_t static_addr2 = 0;
#define IP_ADDR2 static_addr2
#define GW_ADDR2 static_addr2
#endif
/**
* @brief LwIP_DHCP_Process_Handle
* @param None
* @retval None
*/
uint8_t LwIP_DHCP(uint8_t idx, uint8_t dhcp_state)
{
struct ip_addr ipaddr;
struct ip_addr netmask;
struct ip_addr gw;
uint32_t IPaddress;
uint8_t iptab[4];
uint8_t DHCP_state;
struct netif *pnetif = NULL;
struct dhcp *dhcp = NULL;
DHCP_state = dhcp_state;
#if !CONFIG_ETHERNET
if(idx > 1)
idx = 1;
#endif
/* STA+STA: Set different ip network prefix for each interface*/
#if defined(CONFIG_CONCURRENT_MODE) && defined(CONFIG_STA_STA_MODE)
if(idx == 0) {
static_addr2 = 1;
} else {
static_addr2 = 2;
}
#endif
pnetif = &xnetif[idx];
if(DHCP_state == 0){
#if LWIP_VERSION_MAJOR >= 2
ip_addr_set_zero(&pnetif->ip_addr);
ip_addr_set_zero(&pnetif->netmask);
ip_addr_set_zero(&pnetif->gw);
#else
pnetif->ip_addr.addr = 0;
pnetif->netmask.addr = 0;
pnetif->gw.addr = 0;
#endif
}
#if LWIP_VERSION_MAJOR >= 2
dhcp = ((struct dhcp*)netif_get_client_data(pnetif, LWIP_NETIF_CLIENT_DATA_INDEX_DHCP));
if(!netif_is_up(pnetif)) // netif should be set up before doing dhcp request (in lwip v2.0.0)
{
netif_set_up(pnetif);
}
#else
dhcp = pnetif->dhcp;
#endif
for (;;)
{
//printf("\n\r ========DHCP_state:%d============\n\r",DHCP_state);
switch (DHCP_state)
{
case DHCP_START:
{
/*acqurie wakelock to guarantee dhcp*/
rtw_wakelock_timeout(4*1000);
#if CONFIG_WLAN
wifi_unreg_event_handler(WIFI_EVENT_BEACON_AFTER_DHCP, wifi_rx_beacon_hdl);
#endif
#if defined(CONFIG_FAST_DHCP) && CONFIG_FAST_DHCP
if(is_the_same_ap){
if( (offer_ip != 0 && offer_ip != 0xFFFFFFFF) || (dhcp != NULL) ){
if(dhcp == NULL){
dhcp = (struct dhcp *)mem_malloc(sizeof(struct dhcp));
if (dhcp == NULL) {
printf("dhcp_start(): could not allocate dhcp\n");
return -1;
}
}
memset(dhcp, 0, sizeof(struct dhcp));
dhcp->offered_ip_addr.addr = (u32_t)offer_ip;
dhcp->server_ip_addr.addr = (u32_t)server_ip;
#if LWIP_VERSION_MAJOR >= 2
netif_set_client_data(pnetif, LWIP_NETIF_CLIENT_DATA_INDEX_DHCP, dhcp);
#else
pnetif->dhcp = dhcp;
#endif
}
}else{
if(dhcp != NULL){
memset(dhcp, 0, sizeof(struct dhcp));
}
}
#endif
dhcp_start(pnetif);
#if LWIP_VERSION_MAJOR >= 2
dhcp = ((struct dhcp*)netif_get_client_data(pnetif, LWIP_NETIF_CLIENT_DATA_INDEX_DHCP));
#else
dhcp = pnetif->dhcp;
#endif
IPaddress = 0;
DHCP_state = DHCP_WAIT_ADDRESS;
}
break;
case DHCP_WAIT_ADDRESS:
{
/* If DHCP stopped by wifi_disconn_hdl*/
#if LWIP_VERSION_MAJOR >= 2
#include "lwip/prot/dhcp.h"
if(dhcp->state == DHCP_STATE_OFF)
{
IP4_ADDR(ip_2_ip4(&ipaddr), IP_ADDR0, IP_ADDR1, IP_ADDR2, IP_ADDR3);
IP4_ADDR(ip_2_ip4(&netmask), NETMASK_ADDR0, NETMASK_ADDR1 , NETMASK_ADDR2, NETMASK_ADDR3);
IP4_ADDR(ip_2_ip4(&gw), GW_ADDR0, GW_ADDR1, GW_ADDR2, GW_ADDR3);
netif_set_addr(pnetif, ip_2_ip4(&ipaddr), ip_2_ip4(&netmask),ip_2_ip4(&gw));
printf("\n\rLwIP_DHCP: dhcp stop.");
return DHCP_STOP;
}
#else
if(dhcp->state == DHCP_OFF)
{
IP4_ADDR(&ipaddr, IP_ADDR0 ,IP_ADDR1 , IP_ADDR2 , IP_ADDR3 );
IP4_ADDR(&netmask, NETMASK_ADDR0, NETMASK_ADDR1, NETMASK_ADDR2, NETMASK_ADDR3);
IP4_ADDR(&gw, GW_ADDR0, GW_ADDR1, GW_ADDR2, GW_ADDR3);
netif_set_addr(pnetif, &ipaddr , &netmask, &gw);
printf("\n\rLwIP_DHCP: dhcp stop.");
return DHCP_STOP;
}
#endif
/* Read the new IP address */
#if LWIP_VERSION_MAJOR >= 2
IPaddress = ip_addr_get_ip4_u32(netif_ip_addr4(pnetif));
#else
IPaddress = pnetif->ip_addr.addr;
#endif
if (IPaddress!=0)
{
#if LWIP_RANDOMIZE_INITIAL_LOCAL_PORTS
tcp_randomize_local_port();
udp_randomize_local_port();
#endif
DHCP_state = DHCP_ADDRESS_ASSIGNED;
#if CONFIG_WLAN
wifi_reg_event_handler(WIFI_EVENT_BEACON_AFTER_DHCP, wifi_rx_beacon_hdl, NULL);
#endif
/* Stop DHCP */
// dhcp_stop(pnetif); /* can not stop, need to renew, Robbie*/
iptab[0] = (uint8_t)(IPaddress >> 24);
iptab[1] = (uint8_t)(IPaddress >> 16);
iptab[2] = (uint8_t)(IPaddress >> 8);
iptab[3] = (uint8_t)(IPaddress);
printf("\n\rInterface %d IP address : %d.%d.%d.%d", idx, iptab[3], iptab[2], iptab[1], iptab[0]);
#if defined(CONFIG_FAST_DHCP) && CONFIG_FAST_DHCP
#if LWIP_VERSION_MAJOR >= 2
dhcp = ((struct dhcp*)netif_get_client_data(pnetif, LWIP_NETIF_CLIENT_DATA_INDEX_DHCP));
#else
dhcp = pnetif->dhcp;
#endif
restore_wifi_info_to_flash((uint32_t)dhcp->offered_ip_addr.addr, (uint32_t)dhcp->server_ip_addr.addr);
#endif
#if CONFIG_WLAN
error_flag = RTW_NO_ERROR;
#endif
return DHCP_ADDRESS_ASSIGNED;
}
else
{
/* DHCP timeout */
if (dhcp->tries > MAX_DHCP_TRIES)
{
DHCP_state = DHCP_TIMEOUT;
/* Stop DHCP */
dhcp_stop(pnetif);
/* Static address used */
#if LWIP_VERSION_MAJOR >= 2
IP4_ADDR(ip_2_ip4(&ipaddr), IP_ADDR0, IP_ADDR1, IP_ADDR2, IP_ADDR3);
IP4_ADDR(ip_2_ip4(&netmask), NETMASK_ADDR0, NETMASK_ADDR1 , NETMASK_ADDR2, NETMASK_ADDR3);
IP4_ADDR(ip_2_ip4(&gw), GW_ADDR0, GW_ADDR1, GW_ADDR2, GW_ADDR3);
netif_set_addr(pnetif, ip_2_ip4(&ipaddr), ip_2_ip4(&netmask),ip_2_ip4(&gw));
#else
IP4_ADDR(&ipaddr, IP_ADDR0 ,IP_ADDR1 , IP_ADDR2 , IP_ADDR3 );
IP4_ADDR(&netmask, NETMASK_ADDR0, NETMASK_ADDR1, NETMASK_ADDR2, NETMASK_ADDR3);
IP4_ADDR(&gw, GW_ADDR0, GW_ADDR1, GW_ADDR2, GW_ADDR3);
netif_set_addr(pnetif, &ipaddr , &netmask, &gw);
#endif
iptab[0] = IP_ADDR3;
iptab[1] = IP_ADDR2;
iptab[2] = IP_ADDR1;
iptab[3] = IP_ADDR0;
printf("\n\rInterface %d DHCP timeout",idx);
printf("\n\rStatic IP address : %d.%d.%d.%d", iptab[3], iptab[2], iptab[1], iptab[0]);
#if defined(CONFIG_FAST_DHCP) && CONFIG_FAST_DHCP
restore_wifi_info_to_flash((uint32_t)dhcp->offered_ip_addr.addr, (uint32_t)dhcp->server_ip_addr.addr);
#endif
#if CONFIG_WLAN
error_flag = RTW_DHCP_FAIL;
#endif
#if CONFIG_ETHERNET
if(idx == NET_IF_NUM -1) // This is the ethernet interface, set it up for static ip address
netif_set_up(pnetif);
#endif
return DHCP_TIMEOUT;
}
}
}
break;
case DHCP_RELEASE_IP:
#if CONFIG_WLAN
wifi_unreg_event_handler(WIFI_EVENT_BEACON_AFTER_DHCP, wifi_rx_beacon_hdl);
#endif
printf("\n\rLwIP_DHCP: Release ip");
#if LWIP_VERSION_MAJOR >= 2
dhcp_release(pnetif);
#else
if(dhcp && dhcp->state != DHCP_OFF)
dhcp_release_unicast(pnetif);
#endif
return DHCP_RELEASE_IP;
case DHCP_STOP:
#if CONFIG_WLAN
wifi_unreg_event_handler(WIFI_EVENT_BEACON_AFTER_DHCP, wifi_rx_beacon_hdl);
#endif
printf("\n\rLwIP_DHCP: dhcp stop.");
dhcp_stop(pnetif);
return DHCP_STOP;
default:
break;
}
/* wait 250 ms */
vTaskDelay(10);
}
}
void LwIP_ReleaseIP(uint8_t idx)
{
struct ip_addr ipaddr;
struct ip_addr netmask;
struct ip_addr gw;
struct netif *pnetif = &xnetif[idx];
#if LWIP_VERSION_MAJOR >= 2
IP4_ADDR(ip_2_ip4(&ipaddr), 0, 0, 0, 0);
IP4_ADDR(ip_2_ip4(&netmask), 255, 255 , 255, 0);
IP4_ADDR(ip_2_ip4(&gw), 0, 0, 0, 0);
netif_set_addr(pnetif, ip_2_ip4(&ipaddr), ip_2_ip4(&netmask),ip_2_ip4(&gw));
#else
IP4_ADDR(&ipaddr, 0, 0, 0, 0);
IP4_ADDR(&netmask, 255, 255, 255, 0);
IP4_ADDR(&gw, 0, 0, 0, 0);
netif_set_addr(pnetif, &ipaddr , &netmask, &gw);
#endif
}
uint8_t* LwIP_GetMAC(struct netif *pnetif)
{
return (uint8_t *) (pnetif->hwaddr);
}
uint8_t* LwIP_GetIP(struct netif *pnetif)
{
return (uint8_t *) &(pnetif->ip_addr);
}
uint8_t* LwIP_GetGW(struct netif *pnetif)
{
return (uint8_t *) &(pnetif->gw);
}
uint8_t* LwIP_GetMASK(struct netif *pnetif)
{
return (uint8_t *) &(pnetif->netmask);
}
uint8_t* LwIP_GetBC(struct netif *pnetif)
{
#if LWIP_VERSION_MAJOR >= 2
//struct dhcp *dhcp = ((struct dhcp*)netif_get_client_data(pnetif, LWIP_NETIF_CLIENT_DATA_INDEX_DHCP));
return NULL;
#else
return (uint8_t *) &(pnetif->dhcp->offered_bc_addr);
#endif
}
#if LWIP_DNS
void LwIP_GetDNS(struct ip_addr* dns)
{
#if LWIP_VERSION_MAJOR >= 2
struct ip_addr *tmp = (struct ip_addr *)dns_getserver(0);
*dns = *tmp;
#else
*dns = dns_getserver(0);
#endif
}
void LwIP_SetDNS(struct ip_addr* dns)
{
dns_setserver(0, dns);
}
#endif
void LwIP_UseStaticIP(struct netif *pnetif)
{
struct ip_addr ipaddr;
struct ip_addr netmask;
struct ip_addr gw;
/* Static address used */
if(pnetif->name[1] == '0'){
#if CONFIG_WLAN
if((wifi_mode == RTW_MODE_STA)||(wifi_mode == RTW_MODE_STA_AP)){
#if LWIP_VERSION_MAJOR >= 2
IP4_ADDR(ip_2_ip4(&ipaddr), IP_ADDR0, IP_ADDR1, IP_ADDR2, IP_ADDR3);
IP4_ADDR(ip_2_ip4(&netmask), NETMASK_ADDR0, NETMASK_ADDR1 , NETMASK_ADDR2, NETMASK_ADDR3);
IP4_ADDR(ip_2_ip4(&gw), GW_ADDR0, GW_ADDR1, GW_ADDR2, GW_ADDR3);
#else
IP4_ADDR(&ipaddr, IP_ADDR0 ,IP_ADDR1 , IP_ADDR2 , IP_ADDR3 );
IP4_ADDR(&netmask, NETMASK_ADDR0, NETMASK_ADDR1, NETMASK_ADDR2, NETMASK_ADDR3);
IP4_ADDR(&gw, GW_ADDR0, GW_ADDR1, GW_ADDR2, GW_ADDR3);
#endif
}
else if(wifi_mode == RTW_MODE_AP){
#if LWIP_VERSION_MAJOR >= 2
IP4_ADDR(ip_2_ip4(&ipaddr), AP_IP_ADDR0, AP_IP_ADDR1, AP_IP_ADDR2, AP_IP_ADDR3);
IP4_ADDR(ip_2_ip4(&netmask), AP_NETMASK_ADDR0, AP_NETMASK_ADDR1 , AP_NETMASK_ADDR2, AP_NETMASK_ADDR3);
IP4_ADDR(ip_2_ip4(&gw), AP_GW_ADDR0, AP_GW_ADDR1, AP_GW_ADDR2, AP_GW_ADDR3);
#else
IP4_ADDR(&ipaddr, AP_IP_ADDR0, AP_IP_ADDR1, AP_IP_ADDR2, AP_IP_ADDR3);
IP4_ADDR(&netmask, AP_NETMASK_ADDR0, AP_NETMASK_ADDR1 , AP_NETMASK_ADDR2, AP_NETMASK_ADDR3);
IP4_ADDR(&gw, AP_GW_ADDR0, AP_GW_ADDR1, AP_GW_ADDR2, AP_GW_ADDR3);
#endif
}
#endif
}else{
#if LWIP_VERSION_MAJOR >= 2
IP4_ADDR(ip_2_ip4(&ipaddr), AP_IP_ADDR0, AP_IP_ADDR1, AP_IP_ADDR2, AP_IP_ADDR3);
IP4_ADDR(ip_2_ip4(&netmask), AP_NETMASK_ADDR0, AP_NETMASK_ADDR1 , AP_NETMASK_ADDR2, AP_NETMASK_ADDR3);
IP4_ADDR(ip_2_ip4(&gw), AP_GW_ADDR0, AP_GW_ADDR1, AP_GW_ADDR2, AP_GW_ADDR3);
#else
IP4_ADDR(&ipaddr, AP_IP_ADDR0, AP_IP_ADDR1, AP_IP_ADDR2, AP_IP_ADDR3);
IP4_ADDR(&netmask, AP_NETMASK_ADDR0, AP_NETMASK_ADDR1 , AP_NETMASK_ADDR2, AP_NETMASK_ADDR3);
IP4_ADDR(&gw, AP_GW_ADDR0, AP_GW_ADDR1, AP_GW_ADDR2, AP_GW_ADDR3);
#endif
}
#if LWIP_VERSION_MAJOR >= 2
netif_set_addr(pnetif, ip_2_ip4(&ipaddr), ip_2_ip4(&netmask),ip_2_ip4(&gw));
#else
netif_set_addr(pnetif, &ipaddr , &netmask, &gw);
#endif
}
#if LWIP_AUTOIP
#include <lwip/autoip.h>
#if LWIP_VERSION_MAJOR >= 2
#include <lwip/prot/autoip.h>
#endif
void LwIP_AUTOIP(struct netif *pnetif)
{
uint8_t *ip = LwIP_GetIP(pnetif);
struct autoip *autoip = NULL;
autoip_start(pnetif);
#if LWIP_VERSION_MAJOR >= 2
autoip = ((struct autoip*)netif_get_client_data(pnetif, LWIP_NETIF_CLIENT_DATA_INDEX_AUTOIP));
#else
autoip = pnetif->autoip;
#endif
while((autoip->state == AUTOIP_STATE_PROBING) || (autoip->state == AUTOIP_STATE_ANNOUNCING)) {
vTaskDelay(1000);
}
if(*((uint32_t *) ip) == 0) {
struct ip_addr ipaddr;
struct ip_addr netmask;
struct ip_addr gw;
printf("AUTOIP timeout\n");
/* Static address used */
#if LWIP_VERSION_MAJOR >= 2
IP4_ADDR(ip_2_ip4(&ipaddr), IP_ADDR0, IP_ADDR1, IP_ADDR2, IP_ADDR3);
IP4_ADDR(ip_2_ip4(&netmask), NETMASK_ADDR0, NETMASK_ADDR1 , NETMASK_ADDR2, NETMASK_ADDR3);
IP4_ADDR(ip_2_ip4(&gw), GW_ADDR0, GW_ADDR1, GW_ADDR2, GW_ADDR3);
netif_set_addr(pnetif, ip_2_ip4(&ipaddr), ip_2_ip4(&netmask),ip_2_ip4(&gw));
#else
IP4_ADDR(&ipaddr, IP_ADDR0 ,IP_ADDR1 , IP_ADDR2 , IP_ADDR3 );
IP4_ADDR(&netmask, NETMASK_ADDR0, NETMASK_ADDR1, NETMASK_ADDR2, NETMASK_ADDR3);
IP4_ADDR(&gw, GW_ADDR0, GW_ADDR1, GW_ADDR2, GW_ADDR3);
netif_set_addr(pnetif, &ipaddr , &netmask, &gw);
#endif
printf("Static IP address : %d.%d.%d.%d\n", ip[0], ip[1], ip[2], ip[3]);
}
else {
printf("\nLink-local address: %d.%d.%d.%d\n", ip[0], ip[1], ip[2], ip[3]);
}
}
#endif
#if LWIP_IPV6
/* Get IPv6 address with lwip 1.5.0 */
void LwIP_AUTOIP_IPv6(struct netif *pnetif)
{
#if LWIP_VERSION_MAJOR >= 2
uint8_t *ipv6 = (uint8_t *) netif_ip6_addr(pnetif, 0)->addr;
#else
uint8_t *ipv6 = (uint8_t *) &(pnetif->ip6_addr[0].addr[0]);
#endif
netif_create_ip6_linklocal_address(pnetif, 1);
printf("\nIPv6 link-local address: %02x%02x:%02x%02x:%02x%02x:%02x%02x:%02x%02x:%02x%02x:%02x%02x:%02x%02x\n",
ipv6[0], ipv6[1], ipv6[2], ipv6[3], ipv6[4], ipv6[5], ipv6[6], ipv6[7],
ipv6[8], ipv6[9], ipv6[10], ipv6[11], ipv6[12], ipv6[13], ipv6[14], ipv6[15]);
}
#endif
uint32_t LWIP_Get_Dynamic_Sleep_Interval()
{
#ifdef DYNAMIC_TICKLESS_SLEEP_INTERVAL
return DYNAMIC_TICKLESS_SLEEP_INTERVAL;
#else
return 0;
#endif
}

View File

@@ -0,0 +1,79 @@
/******************************************************************************
*
* This module is a confidential and proprietary property of RealTek and
* possession or use of this module requires written permission of RealTek.
*
* Copyright(c) 2016, Realtek Semiconductor Corporation. All rights reserved.
*
******************************************************************************/
/* Define to prevent recursive inclusion -------------------------------------*/
#ifndef __NETCONF_H
#define __NETCONF_H
#ifdef __cplusplus
extern "C" {
#endif
#include "tcpip.h"
/* Includes ------------------------------------------------------------------*/
#include <platform/platform_stdlib.h>
#include "platform_opts.h"
#include "autoconf.h"
// macros
/* Give default value if not defined */
#ifndef NET_IF_NUM
#ifdef CONFIG_CONCURRENT_MODE
#define NET_IF_NUM ((CONFIG_ETHERNET) + (CONFIG_WLAN) + 1)
#else
#define NET_IF_NUM ((CONFIG_ETHERNET) + (CONFIG_WLAN))
#endif // end of CONFIG_CONCURRENT_MODE
#endif // end of NET_IF_NUM
/* Private typedef -----------------------------------------------------------*/
typedef enum
{
DHCP_START=0,
DHCP_WAIT_ADDRESS,
DHCP_ADDRESS_ASSIGNED,
DHCP_RELEASE_IP,
DHCP_STOP,
DHCP_TIMEOUT
} DHCP_State_TypeDef;
/* Extern functions ------------------------------------------------------------*/
void wifi_rx_beacon_hdl( char* buf, int buf_len, int flags, void* userdata);
/* Exported types ------------------------------------------------------------*/
/* Exported constants --------------------------------------------------------*/
/* Exported macro ------------------------------------------------------------*/
/* Exported functions ------------------------------------------------------- */
void LwIP_Init(void);
uint8_t LwIP_DHCP(uint8_t idx, uint8_t dhcp_state);
unsigned char* LwIP_GetMAC(struct netif *pnetif);
unsigned char* LwIP_GetIP(struct netif *pnetif);
unsigned char* LwIP_GetGW(struct netif *pnetif);
uint8_t* LwIP_GetMASK(struct netif *pnetif);
uint8_t* LwIP_GetBC(struct netif *pnetif);
#if LWIP_DNS
void LwIP_GetDNS(struct ip_addr* dns);
void LwIP_SetDNS(struct ip_addr* dns);
#endif
void LwIP_UseStaticIP(struct netif *pnetif);
#if LWIP_AUTOIP
void LwIP_AUTOIP(struct netif *pnetif);
#endif
#if LWIP_IPV6
void LwIP_AUTOIP_IPv6(struct netif *pnetif);
#endif
uint32_t LWIP_Get_Dynamic_Sleep_Interval();
#ifdef __cplusplus
}
#endif
#endif /* __NETCONF_H */
/******************* (C) COPYRIGHT 2011 STMicroelectronics *****END OF FILE****/

View File

@@ -0,0 +1,341 @@
/******************************************************************************
*
* This module is a confidential and proprietary property of RealTek and
* possession or use of this module requires written permission of RealTek.
*
* Copyright(c) 2016, Realtek Semiconductor Corporation. All rights reserved.
*
******************************************************************************/
#ifndef __LWIPOPTS_H__
#define __LWIPOPTS_H__
#include <platform/platform_stdlib.h>
#include "platform_opts.h"
#define WIFI_LOGO_CERTIFICATION_CONFIG 0 //for ping 10k test buffer setting
/**
* SYS_LIGHTWEIGHT_PROT==1: if you want inter-task protection for certain
* critical regions during buffer allocation, deallocation and memory
* allocation and deallocation.
*/
#define SYS_LIGHTWEIGHT_PROT 1
/* Define LWIP_COMPAT_MUTEX if the port has no mutexes and binary semaphores
should be used instead */
#define LWIP_COMPAT_MUTEX 1
#define LWIP_COMPAT_MUTEX 1
#define ETHARP_TRUST_IP_MAC 0
#define IP_REASSEMBLY 1
#define IP_FRAG 1
#define ARP_QUEUEING 0
/**
* NO_SYS==1: Provides VERY minimal functionality. Otherwise,
* use lwIP facilities.
*/
#define NO_SYS 0
#ifndef CONFIG_DYNAMIC_TICKLESS
#define CONFIG_DYNAMIC_TICKLESS 0
#endif
/* ---------- Memory options ---------- */
/* MEM_ALIGNMENT: should be set to the alignment of the CPU for which
lwIP is compiled. 4 byte alignment -> define MEM_ALIGNMENT to 4, 2
byte alignment -> define MEM_ALIGNMENT to 2. */
#define MEM_ALIGNMENT 4
/* MEM_SIZE: the size of the heap memory. If the application will send
a lot of data that needs to be copied, this should be set high. */
#if WIFI_LOGO_CERTIFICATION_CONFIG
#define MEM_SIZE (20*1024) //for ping 10k test
#elif CONFIG_ETHERNET
#define MEM_SIZE (6*1024) //for iperf test
#else
#define MEM_SIZE (5*1024)
#endif
/* MEMP_NUM_PBUF: the number of memp struct pbufs. If the application
sends a lot of data out of ROM (or other static memory), this
should be set high. */
#define MEMP_NUM_PBUF 100
/* MEMP_NUM_UDP_PCB: the number of UDP protocol control blocks. One
per active UDP "connection". */
#define MEMP_NUM_UDP_PCB 6
/* MEMP_NUM_TCP_PCB: the number of simulatenously active TCP
connections. */
#define MEMP_NUM_TCP_PCB 10
/* MEMP_NUM_TCP_PCB_LISTEN: the number of listening TCP
connections. */
#define MEMP_NUM_TCP_PCB_LISTEN 5
/* MEMP_NUM_TCP_SEG: the number of simultaneously queued TCP
segments. */
#define MEMP_NUM_TCP_SEG 20
/* MEMP_NUM_SYS_TIMEOUT: the number of simulateously active
timeouts. */
#define MEMP_NUM_SYS_TIMEOUT 10
/* ---------- Pbuf options ---------- */
/* PBUF_POOL_SIZE: the number of buffers in the pbuf pool. */
#if WIFI_LOGO_CERTIFICATION_CONFIG
#define PBUF_POOL_SIZE 40 //for ping 10k test
#else
#define PBUF_POOL_SIZE 20
#endif
/* IP_REASS_MAX_PBUFS: Total maximum amount of pbufs waiting to be reassembled.*/
#if WIFI_LOGO_CERTIFICATION_CONFIG
#define IP_REASS_MAX_PBUFS 40 //for ping 10k test
#else
#define IP_REASS_MAX_PBUFS 10
#endif
/* PBUF_POOL_BUFSIZE: the size of each pbuf in the pbuf pool. */
#define PBUF_POOL_BUFSIZE 500
/* ---------- TCP options ---------- */
#define LWIP_TCP 1
#define TCP_TTL 255
/* Controls if TCP should queue segments that arrive out of
order. Define to 0 if your device is low on memory. */
#define TCP_QUEUE_OOSEQ 1
/* TCP Maximum segment size. */
#define TCP_MSS (1500 - 40) /* TCP_MSS = (Ethernet MTU - IP header size - TCP header size) */
/* TCP sender buffer space (bytes). */
#define TCP_SND_BUF (5*TCP_MSS)
/* TCP_SND_QUEUELEN: TCP sender buffer space (pbufs). This must be at least
as much as (2 * TCP_SND_BUF/TCP_MSS) for things to work. */
#define TCP_SND_QUEUELEN (4* TCP_SND_BUF/TCP_MSS)
/* TCP receive window. */
#define TCP_WND (4*TCP_MSS)
/* ---------- ICMP options ---------- */
#define LWIP_ICMP 1
/* ---------- ARP options ----------- */
#define LWIP_ARP 1
/* ---------- DHCP options ---------- */
/* Define LWIP_DHCP to 1 if you want DHCP configuration of
interfaces. DHCP is not implemented in lwIP 0.5.1, however, so
turning this on does currently not work. */
#define LWIP_DHCP 1
/* ---------- UDP options ---------- */
#define LWIP_UDP 1
#define UDP_TTL 255
/* ---------- DNS options ---------- */
#define LWIP_DNS 1
/* ---------- UPNP options --------- */
#define LWIP_UPNP 0
/* ---------- SO_SNDRCVTIMEO_NONSTANDARD options --------- */
#define LWIP_SO_SNDRCVTIMEO_NONSTANDARD 1
/* ---------- SO_REUSE options --------- */
#define SO_REUSE 1
/* Support Multicast */
#define LWIP_IGMP 1
#define LWIP_RAND() rand()
extern unsigned int sys_now(void);
#define LWIP_SRAND() srand(sys_now())
#define LWIP_MTU_ADJUST 1
/* Support TCP Keepalive */
#define LWIP_TCP_KEEPALIVE 1
/*LWIP_UART_ADAPTER==1: Enable LWIP_UART_ADAPTER when CONFIG_GAGENT is enabled,
because some GAGENT functions denpond on the following macro definitions.*/
#define LWIP_UART_ADAPTER 0
#if LWIP_UART_ADAPTER || CONFIG_ETHERNET
#undef LWIP_SO_SNDTIMEO
#define LWIP_SO_SNDTIMEO 1
#undef SO_REUSE
#define SO_REUSE 1
#undef MEMP_NUM_NETCONN
#define MEMP_NUM_NETCONN 10
#undef TCP_WND
#define TCP_WND (4*TCP_MSS)
#define TCP_KEEPIDLE_DEFAULT 10000UL
#define TCP_KEEPINTVL_DEFAULT 1000UL
#define TCP_KEEPCNT_DEFAULT 10U
#endif
#if CONFIG_EXAMPLE_UART_ATCMD || CONFIG_EXAMPLE_SPI_ATCMD
#undef LWIP_SO_SNDTIMEO
#define LWIP_SO_SNDTIMEO 1
#undef SO_REUSE
#define SO_REUSE 1
#undef SO_REUSE_RXTOALL
#define SO_REUSE_RXTOALL 1
#undef MEMP_NUM_NETCONN
#define MEMP_NUM_NETCONN 10
#undef MEMP_NUM_TCP_PCB
#define MEMP_NUM_TCP_PCB (MEMP_NUM_NETCONN)
#undef MEMP_NUM_UDP_PCB
#define MEMP_NUM_UDP_PCB (MEMP_NUM_NETCONN)
#undef TCP_WND
#define TCP_WND (4*TCP_MSS)
#define TCP_KEEPIDLE_DEFAULT 10000UL
#define TCP_KEEPINTVL_DEFAULT 1000UL
#define TCP_KEEPCNT_DEFAULT 10U
#define ERRNO 1
#endif
#if (CONFIG_EXAMPLE_ANDLINK || CONFIG_LIBCOAP)
#define MEMP_USE_CUSTOM_POOLS 1
#endif
/* ---------- Statistics options ---------- */
#define LWIP_STATS 0
#define LWIP_PROVIDE_ERRNO 1
/*
--------------------------------------
---------- Checksum options ----------
--------------------------------------
*/
/*
The STM32F2x7 allows computing and verifying the IP, UDP, TCP and ICMP checksums by hardware:
- To use this feature let the following define uncommented.
- To disable it and process by CPU comment the the checksum.
*/
//Do checksum by lwip - WLAN nic does not support Checksum offload
//#define CHECKSUM_BY_HARDWARE
#ifdef CHECKSUM_BY_HARDWARE
/* CHECKSUM_GEN_IP==0: Generate checksums by hardware for outgoing IP packets.*/
#define CHECKSUM_GEN_IP 0
/* CHECKSUM_GEN_UDP==0: Generate checksums by hardware for outgoing UDP packets.*/
#define CHECKSUM_GEN_UDP 0
/* CHECKSUM_GEN_TCP==0: Generate checksums by hardware for outgoing TCP packets.*/
#define CHECKSUM_GEN_TCP 0
/* CHECKSUM_CHECK_IP==0: Check checksums by hardware for incoming IP packets.*/
#define CHECKSUM_CHECK_IP 0
/* CHECKSUM_CHECK_UDP==0: Check checksums by hardware for incoming UDP packets.*/
#define CHECKSUM_CHECK_UDP 0
/* CHECKSUM_CHECK_TCP==0: Check checksums by hardware for incoming TCP packets.*/
#define CHECKSUM_CHECK_TCP 0
#else
/* CHECKSUM_GEN_IP==1: Generate checksums in software for outgoing IP packets.*/
#define CHECKSUM_GEN_IP 1
/* CHECKSUM_GEN_UDP==1: Generate checksums in software for outgoing UDP packets.*/
#define CHECKSUM_GEN_UDP 1
/* CHECKSUM_GEN_TCP==1: Generate checksums in software for outgoing TCP packets.*/
#define CHECKSUM_GEN_TCP 1
/* CHECKSUM_CHECK_IP==1: Check checksums in software for incoming IP packets.*/
#define CHECKSUM_CHECK_IP 1
/* CHECKSUM_CHECK_UDP==1: Check checksums in software for incoming UDP packets.*/
#define CHECKSUM_CHECK_UDP 1
/* CHECKSUM_CHECK_TCP==1: Check checksums in software for incoming TCP packets.*/
#define CHECKSUM_CHECK_TCP 1
#endif
/*
----------------------------------------------
---------- Sequential layer options ----------
----------------------------------------------
*/
/**
* LWIP_NETCONN==1: Enable Netconn API (require to use api_lib.c)
*/
#define LWIP_NETCONN 1
/*
------------------------------------
---------- Socket options ----------
------------------------------------
*/
/**
* LWIP_SOCKET==1: Enable Socket API (require to use sockets.c)
*/
#define LWIP_SOCKET 1
/*
-----------------------------------
---------- DEBUG options ----------
-----------------------------------
*/
#define LWIP_DEBUG 1
/*
---------------------------------
---------- OS options ----------
---------------------------------
*/
#define TCPIP_THREAD_STACKSIZE 1000
#define TCPIP_MBOX_SIZE 6
#define DEFAULT_UDP_RECVMBOX_SIZE 6
#define DEFAULT_TCP_RECVMBOX_SIZE 6
#define DEFAULT_RAW_RECVMBOX_SIZE 6
#define DEFAULT_ACCEPTMBOX_SIZE 6
#define DEFAULT_THREAD_STACKSIZE 500
#define TCPIP_THREAD_PRIO (configMAX_PRIORITIES - 2)
/* Added by Realtek */
#define LWIP_RANDOMIZE_INITIAL_LOCAL_PORTS 1
#ifndef DNS_IGNORE_REPLY_ERR
#define DNS_IGNORE_REPLY_ERR 1
#endif /* DNS_IGNORE_REPLY_ERR */
/* Added by Realtek. For DHCP server reply unicast DHCP packets before the ip actually assigned. */
#define ETHARP_SUPPORT_STATIC_ENTRIES 1
/* Extra options for lwip_v2.0.2 which should not affect lwip_v1.4.1 */
#define LWIP_TCPIP_CORE_LOCKING 0
#define LWIP_TCPIP_TIMEOUT 1
#define LWIP_SO_RCVTIMEO 1
#define LWIP_SOCKET_SET_ERRNO 0
#undef LWIP_DEBUG
#define LWIP_RAW 1
#define LWIP_AUTOIP 1
#define TCPIP_THREAD_NAME "TCP_IP"
#define LWIP_IPV6 0
#if LWIP_IPV6
#undef MEMP_NUM_SYS_TIMEOUT
#define MEMP_NUM_SYS_TIMEOUT 13
#endif
#include "lwip/init.h" //for version control
#endif /* __LWIPOPTS_H__ */
/******************* (C) COPYRIGHT 2011 STMicroelectronics *****END OF FILE****/

View File

@@ -0,0 +1,68 @@
#ifndef MAIN_H
#define MAIN_H
#include <autoconf.h>
#define CONFIG_WLAN 1
/* Header file declaration*/
void wlan_network();
/* Interactive Mode */
#define SERIAL_DEBUG_RX 1
#if defined(__ICCARM__)
static
#endif
char uart_buf[64];
/* WLAN and Netork */
#define STA_MODE_SSID "ap" /* Set SSID here */
#define AP_MODE_SSID "wlan_ap_ssid" /* Set SSID here */
#define AP_DEFAULT_CH 6
#define WLAN0_NAME "wlan0"
#define WLAN1_NAME "wlan1"
#define WPA_PASSPHRASE "1234567890" /* Max 32 cahracters */
#define WEP40_KEY {0x12, 0x34, 0x56, 0x78, 0x90}
/*Static IP ADDRESS*/
#define IP_ADDR0 192
#define IP_ADDR1 168
#define IP_ADDR2 1
#define IP_ADDR3 80
/*NETMASK*/
#define NETMASK_ADDR0 255
#define NETMASK_ADDR1 255
#define NETMASK_ADDR2 255
#define NETMASK_ADDR3 0
/*Gateway Address*/
#define GW_ADDR0 192
#define GW_ADDR1 168
#define GW_ADDR2 1
#define GW_ADDR3 1
/*******************************************/
/*Static IP ADDRESS*/
#define AP_IP_ADDR0 192
#define AP_IP_ADDR1 168
#define AP_IP_ADDR2 43
#define AP_IP_ADDR3 1
/*NETMASK*/
#define AP_NETMASK_ADDR0 255
#define AP_NETMASK_ADDR1 255
#define AP_NETMASK_ADDR2 255
#define AP_NETMASK_ADDR3 0
/*Gateway Address*/
#define AP_GW_ADDR0 192
#define AP_GW_ADDR1 168
#define AP_GW_ADDR2 43
#define AP_GW_ADDR3 1
#endif

View File

@@ -0,0 +1,21 @@
//----------------------------------------------------------------------------//
#ifndef __MAIN_TEST_H
#define __MAIN_TEST_H
#ifdef __cplusplus
extern "C" {
#endif
/* Exported test functions ------------------------------------------------------- */
void do_ping_test(char *ip, int size, int count, int interval);
void do_ping_call(char *ip, int loop, int count);
void interactive_question(char *question, char *choice, char *buf, int buf_size);
void start_interactive_mode(void);
#ifdef __cplusplus
}
#endif
#endif // __MAIN_TEST_H
//----------------------------------------------------------------------------//

View File

@@ -0,0 +1,50 @@
/**
******************************************************************************
* @file netconf.h
* @author MCD Application Team
* @version V1.1.0
* @date 07-October-2011
* @brief This file contains all the functions prototypes for the netconf.c
* file.
******************************************************************************
* @attention
*
* THE PRESENT FIRMWARE WHICH IS FOR GUIDANCE ONLY AIMS AT PROVIDING CUSTOMERS
* WITH CODING INFORMATION REGARDING THEIR PRODUCTS IN ORDER FOR THEM TO SAVE
* TIME. AS A RESULT, STMICROELECTRONICS SHALL NOT BE HELD LIABLE FOR ANY
* DIRECT, INDIRECT OR CONSEQUENTIAL DAMAGES WITH RESPECT TO ANY CLAIMS ARISING
* FROM THE CONTENT OF SUCH FIRMWARE AND/OR THE USE MADE BY CUSTOMERS OF THE
* CODING INFORMATION CONTAINED HEREIN IN CONNECTION WITH THEIR PRODUCTS.
*
* <h2><center>&copy; COPYRIGHT 2011 STMicroelectronics</center></h2>
******************************************************************************
*/
/* Define to prevent recursive inclusion -------------------------------------*/
#ifndef __NETCONF_H
#define __NETCONF_H
#ifdef __cplusplus
extern "C" {
#endif
// TODO: remove this file
#include "lwip_netconf.h"
#if 0
/* Includes ------------------------------------------------------------------*/
#include "main.h"
/* Exported types ------------------------------------------------------------*/
/* Exported constants --------------------------------------------------------*/
/* Exported macro ------------------------------------------------------------*/
/* Exported functions ------------------------------------------------------- */
void LwIP_Init(void);
void LwIP_DHCP(void);
#endif
#ifdef __cplusplus
}
#endif
#endif /* __NETCONF_H */
/******************* (C) COPYRIGHT 2011 STMicroelectronics *****END OF FILE****/

View File

@@ -0,0 +1,8 @@
#ifndef __RTL8195A_IT_H_
#define __RTL8195A_IT_H_
int irq_alloc_wlan(void *contex);
#endif //__RTL8195A_IT_H_

View File

@@ -0,0 +1,46 @@
#ifndef _UTIL_H
#define _UTIL_H
#include <wireless.h>
#include <wlan_intf.h>
#ifdef __cplusplus
extern "C" {
#endif
#include "wifi_util.h"
#if 0
typedef enum _WIFI_EVENT_INDICATE{
WIFI_EVENT_CONNECT = 0,
WIFI_EVENT_DISCONNECT = 1,
WIFI_EVENT_FOURWAY_HANDSHAKE_DONE = 2,
}WIFI_EVENT_INDICATE;
int wext_get_ssid(const char *ifname, __u8 *ssid);
int wext_set_ssid(const char *ifname, const __u8 *ssid, __u16 ssid_len);
int wext_set_auth_param(const char *ifname, __u16 idx, __u32 value);
int wext_set_key_ext(const char *ifname, __u16 alg, const __u8 *addr, int key_idx, int set_tx, const __u8 *seq, __u16 seq_len, __u8 *key, __u16 key_len);
int wext_get_enc_ext(const char *ifname, __u16 *alg);
int wext_set_passphrase(const char *ifname, const __u8 *passphrase, __u16 passphrase_len);
int wext_get_passphrase(const char *ifname, __u8 *passphrase);
int wext_set_mode(const char *ifname, int mode);
int wext_get_mode(const char *ifname, int *mode);
int wext_set_ap_ssid(const char *ifname, const __u8 *ssid, __u16 ssid_len);
int wext_set_country(const char *ifname, char *country_code);
int wext_get_rssi(const char *ifname, int *rssi);
int wext_set_channel(const char *ifname, __u8 ch);
int wext_get_channel(const char *ifname, __u8 *ch);
int wext_set_scan(const char *ifname, char *buf, __u16 buf_len);
int wext_get_scan(const char *ifname, char *buf, __u16 buf_len);
int wext_mp_command(const char *ifname, char *cmd, int show_msg);
int wext_wifi_priv(const char *ifname, int argc, char **argv);
void wext_wlan_indicate(unsigned int cmd, union iwreq_data *wrqu, char *extra);
#endif
#define wext_handshake_done rltk_wlan_handshake_done
#ifdef __cplusplus
}
#endif
#endif /* _UTIL_H */

View File

@@ -0,0 +1,262 @@
#include "FreeRTOS.h"
#include "task.h"
#include "main.h"
#include <lwip/sockets.h>
#include <lwip/raw.h>
#include <lwip/icmp.h>
#include <lwip/inet_chksum.h>
#include <lwip/netdb.h>
#include <platform/platform_stdlib.h>
#define PING_IP "192.168.159.1"
#define PING_TO 1000
#define PING_ID 0xABCD
#define BUF_SIZE 10000
#define STACKSIZE 1024
static unsigned short ping_seq = 0;
static int infinite_loop, ping_count, data_size, ping_interval, ping_call;
static int ping_total_time = 0, ping_received_count = 0;
static void generate_ping_echo(unsigned char *buf, int size)
{
int i;
struct icmp_echo_hdr *pecho;
for(i = 0; i < size; i ++) {
buf[sizeof(struct icmp_echo_hdr) + i] = (unsigned char) i;
}
pecho = (struct icmp_echo_hdr *) buf;
ICMPH_TYPE_SET(pecho, ICMP_ECHO);
ICMPH_CODE_SET(pecho, 0);
pecho->chksum = 0;
pecho->id = PING_ID;
pecho->seqno = htons(++ ping_seq);
//Checksum includes icmp header and data. Need to calculate after fill up icmp header
pecho->chksum = inet_chksum(pecho, sizeof(struct icmp_echo_hdr) + size);
}
void ping_test(void *param)
{
int i, ping_socket;
int pint_timeout = PING_TO;
struct sockaddr_in to_addr, from_addr;
int from_addr_len = sizeof(struct sockaddr);
int ping_size, reply_size;
unsigned char *ping_buf, *reply_buf;
unsigned int ping_time, reply_time;
struct ip_hdr *iphdr;
struct icmp_echo_hdr *pecho;
unsigned int min_time = 1000, max_time = 0;
struct hostent *server_host;
char *host = param;
ping_total_time = 0;
ping_received_count = 0;
if(data_size > BUF_SIZE){
printf("\n\r[ERROR] %s: data size error, can't exceed %d",__func__,BUF_SIZE);
return;
}
//Ping size = icmp header(8 bytes) + data size
ping_size = sizeof(struct icmp_echo_hdr) + data_size;
ping_buf = pvPortMalloc(ping_size);
if(NULL == ping_buf){
printf("\n\r[ERROR] %s: Allocate ping_buf failed",__func__);
return;
}
reply_buf = pvPortMalloc(ping_size);
if(NULL == reply_buf){
vPortFree(ping_buf);
printf("\n\r[ERROR] %s: Allocate reply_buf failed",__func__);
return;
}
printf("\n\r[%s] PING %s %d(%d) bytes of data\n", __FUNCTION__, host, data_size, sizeof(struct ip_hdr) + sizeof(struct icmp_echo_hdr) + data_size);
for(i = 0; (i < ping_count) || (infinite_loop == 1); i ++) {
ping_socket = socket(AF_INET, SOCK_RAW, IP_PROTO_ICMP);
#if defined(LWIP_SO_SNDRCVTIMEO_NONSTANDARD) && (LWIP_SO_SNDRCVTIMEO_NONSTANDARD == 0) // lwip 1.5.0
struct timeval timeout;
timeout.tv_sec = pint_timeout / 1000;
timeout.tv_usec = pint_timeout % 1000 * 1000;
setsockopt(ping_socket, SOL_SOCKET, SO_RCVTIMEO, &timeout, sizeof(timeout));
#else // lwip 1.4.1
setsockopt(ping_socket, SOL_SOCKET, SO_RCVTIMEO, &pint_timeout, sizeof(pint_timeout));
#endif
to_addr.sin_len = sizeof(to_addr);
to_addr.sin_family = AF_INET;
if (inet_aton(host, &to_addr.sin_addr) == 0) {
server_host = gethostbyname(host);
if(server_host == NULL){
printf("\n\r[%s] Get host name failed in the %d ping test\n", __FUNCTION__, (i + 1));
close(ping_socket);
vTaskDelay(ping_interval * configTICK_RATE_HZ);
continue;
}
memcpy((void *) &to_addr.sin_addr, (void *) server_host->h_addr, server_host->h_length);
}
else
to_addr.sin_addr.s_addr = inet_addr(host);
generate_ping_echo(ping_buf, data_size);
sendto(ping_socket, ping_buf, ping_size, 0, (struct sockaddr *) &to_addr, sizeof(to_addr));
ping_time = xTaskGetTickCount();
if((reply_size = recvfrom(ping_socket, reply_buf, ping_size, 0, (struct sockaddr *) &from_addr, (socklen_t *) &from_addr_len))
>= (int)(sizeof(struct ip_hdr) + sizeof(struct icmp_echo_hdr)) && (from_addr.sin_addr.s_addr == to_addr.sin_addr.s_addr)) {
reply_time = xTaskGetTickCount();
iphdr = (struct ip_hdr *)reply_buf;
pecho = (struct icmp_echo_hdr *)(reply_buf + (IPH_HL(iphdr) * 4));
if((pecho->id == PING_ID) && (pecho->seqno == htons(ping_seq))) {
printf("\n\r[%s] %d bytes from %s: icmp_seq=%d time=%d ms", __FUNCTION__, reply_size - sizeof(struct icmp_echo_hdr), inet_ntoa(from_addr.sin_addr), htons(pecho->seqno), (reply_time - ping_time) * portTICK_RATE_MS);
ping_received_count++;
ping_total_time += (reply_time - ping_time) * portTICK_RATE_MS;
if((reply_time - ping_time) > max_time) max_time = (reply_time - ping_time);
if((reply_time - ping_time) < min_time) min_time = (reply_time - ping_time);
}
}
else
printf("\n\r[%s] Request timeout for icmp_seq %d\n", __FUNCTION__, ping_seq);
close(ping_socket);
vTaskDelay(ping_interval * configTICK_RATE_HZ);
}
printf("\n\r[%s] %d packets transmitted, %d received, %d%% packet loss, average %d ms", __FUNCTION__, ping_count, ping_received_count, (ping_count-ping_received_count)*100/ping_count, ping_total_time/ping_received_count);
printf("\n\r[%s] min: %d ms, max: %d ms\n\r", __FUNCTION__, min_time, max_time);
vPortFree(ping_buf);
vPortFree(reply_buf);
vPortFree(host);
if(!ping_call)
vTaskDelete(NULL);
}
void do_ping_call(char *ip, int loop, int count)
{
ping_call = 1;
ping_seq = 0;
data_size = 120;
ping_interval = 1;
infinite_loop = loop;
ping_count = count;
char * host;
host = pvPortMalloc(strlen(ip) + 1);
memset(host, 0, (strlen(ip) + 1));
memcpy(host, ip, strlen(ip));
ping_test(host);
}
int get_ping_report(int *ping_lost){
*ping_lost = ping_count - ping_received_count;
return 0;
}
void cmd_ping(int argc, char **argv)
{
int argv_count = 2;
char * host;
if(argc < 2)
goto Exit;
//ping cmd default value
infinite_loop = 0;
ping_count = 4;
data_size = 32;
ping_interval = 1;
ping_call = 1;
ping_seq = 0;
while(argv_count<=argc){
//first operation
if(argv_count == 2){
host = pvPortMalloc(strlen(argv[argv_count-1]) + 1);
memset(host, 0, (strlen(argv[argv_count-1]) + 1));
strncpy(host, argv[argv_count-1], strlen(argv[argv_count-1]));
argv_count++;
}
else{
if(strcmp(argv[argv_count-1], "-t") == 0){
infinite_loop = 1;
argv_count++;
}
else if(strcmp(argv[argv_count-1], "-n") == 0){
if(argc < (argv_count+1))
goto Exit;
ping_count = (int) atoi(argv[argv_count]);
argv_count+=2;
}
else if(strcmp(argv[argv_count-1], "-l") == 0){
if(argc < (argv_count+1))
goto Exit;
data_size = (int) atoi(argv[argv_count]);
argv_count+=2;
}
else{
goto Exit;
}
}
}
ping_test(host);
return;
Exit:
printf("\n\r[ATWI] Usage: ATWI=[host],[options]\n");
printf("\n\r -t Ping the specified host until stopped\n");
printf(" \r -n # Number of echo requests to send (default 4 times)\n");
printf(" \r -l # Send buffer size (default 32 bytes)\n");
printf("\n\r Example:\n");
printf(" \r ATWI=192.168.1.2,-n,100,-l,5000\n");
return;
}
void do_ping_test(char *ip, int size, int count, int interval)
{
char *host;
if((sizeof(struct icmp_echo_hdr) + size) > BUF_SIZE) {
printf("\n\r%s BUF_SIZE(%d) is too small", __FUNCTION__, BUF_SIZE);
return;
}
if(ip == NULL){
host = pvPortMalloc(strlen(PING_IP) + 1);
memset(host, 0, (strlen(PING_IP) + 1));
strcpy(host, PING_IP);
}
else{
host = pvPortMalloc(strlen(ip) + 1);
memset(host, 0, (strlen(ip) + 1));
strcpy(host, ip);
}
ping_call = 0;
ping_seq = 0;
data_size = size;
ping_interval = interval;
if(count == 0) {
infinite_loop = 1;
ping_count = 0;
}
else {
infinite_loop = 0;
ping_count = count;
}
if(xTaskCreate(ping_test, ((const signed char*)"ping_test"), STACKSIZE, host, tskIDLE_PRIORITY + 1, NULL) != pdPASS)
printf("\n\r%s xTaskCreate failed", __FUNCTION__);
}

View File

@@ -0,0 +1,71 @@
/******************************************************************************
*
* This module is a confidential and proprietary property of RealTek and
* possession or use of this module requires written permission of RealTek.
*
* Copyright(c) 2016, Realtek Semiconductor Corporation. All rights reserved.
*
******************************************************************************/
#include "FreeRTOS.h"
#include "task.h"
#include "semphr.h"
#include "main.h"
#include "main_test.h"
#if CONFIG_WLAN
#include "wifi_conf.h"
#include "wlan_intf.h"
#include "wifi_constants.h"
#endif
#include "lwip_netconf.h"
#include <platform/platform_stdlib.h>
#ifndef CONFIG_INIT_NET
#define CONFIG_INIT_NET 1
#endif
#ifndef CONFIG_INTERACTIVE_MODE
#define CONFIG_INTERACTIVE_MODE 1
#endif
#define STACKSIZE (512 + 768)
xSemaphoreHandle uart_rx_interrupt_sema = NULL;
void init_thread(void *param)
{
#if CONFIG_INIT_NET
#if CONFIG_LWIP_LAYER
/* Initilaize the LwIP stack */
LwIP_Init();
#endif
#endif
#if CONFIG_WIFI_IND_USE_THREAD
wifi_manager_init();
#endif
#if CONFIG_WLAN
wifi_on(RTW_MODE_STA);
#if CONFIG_AUTO_RECONNECT
//setup reconnection flag
wifi_set_autoreconnect(1);
#endif
printf("\n\r%s(%d), Available heap 0x%x", __FUNCTION__, __LINE__, xPortGetFreeHeapSize());
#endif
#if CONFIG_INTERACTIVE_MODE
/* Initial uart rx swmaphore*/
vSemaphoreCreateBinary(uart_rx_interrupt_sema);
xSemaphoreTake(uart_rx_interrupt_sema, 1/portTICK_RATE_MS);
start_interactive_mode();
#endif
/* Kill init thread after all init tasks done */
vTaskDelete(NULL);
}
void wlan_network()
{
if(xTaskCreate(init_thread, ((const char*)"init"), STACKSIZE, NULL, tskIDLE_PRIORITY + 3 + PRIORITY_OFFSET, NULL) != pdPASS)
printf("\n\r%s xTaskCreate(init_thread) failed", __FUNCTION__);
}

View File

@@ -0,0 +1,262 @@
#ifndef __LIST_H
#define __LIST_H
#if defined ( __CC_ARM )
#ifndef inline
#define inline __inline
#endif
#endif
/* This file is from Linux Kernel (include/linux/list.h)
* and modified by simply removing hardware prefetching of list items.
* Here by copyright, credits attributed to wherever they belong.
* Kulesh Shanmugasundaram (kulesh [squiggly] isis.poly.edu)
*/
/*
* Simple doubly linked list implementation.
*
* Some of the internal functions ("__xxx") are useful when
* manipulating whole lists rather than single entries, as
* sometimes we already know the next/prev entries and we can
* generate better code by using them directly rather than
* using the generic single-entry routines.
*/
struct list_head {
struct list_head *next, *prev;
};
#define LIST_HEAD_INIT(name) { &(name), &(name) }
#define LIST_HEAD(name) \
struct list_head name = LIST_HEAD_INIT(name)
#define INIT_LIST_HEAD(ptr) do { \
(ptr)->next = (ptr); (ptr)->prev = (ptr); \
} while (0)
/*
* Insert a new entry between two known consecutive entries.
*
* This is only for internal list manipulation where we know
* the prev/next entries already!
*/
static inline void __list_add(struct list_head *newitem,
struct list_head *prev,
struct list_head *next)
{
next->prev = newitem;
newitem->next = next;
newitem->prev = prev;
prev->next = newitem;
}
/**
* list_add - add a new entry
* @new: new entry to be added
* @head: list head to add it after
*
* Insert a new entry after the specified head.
* This is good for implementing stacks.
*/
static inline void list_add(struct list_head *newitem, struct list_head *head)
{
__list_add(newitem, head, head->next);
}
/**
* list_add_tail - add a new entry
* @new: new entry to be added
* @head: list head to add it before
*
* Insert a new entry before the specified head.
* This is useful for implementing queues.
*/
static inline void list_add_tail(struct list_head *newitem, struct list_head *head)
{
__list_add(newitem, head->prev, head);
}
/*
* Delete a list entry by making the prev/next entries
* point to each other.
*
* This is only for internal list manipulation where we know
* the prev/next entries already!
*/
static inline void __list_del(struct list_head *prev, struct list_head *next)
{
next->prev = prev;
prev->next = next;
}
/**
* list_del - deletes entry from list.
* @entry: the element to delete from the list.
* Note: list_empty on entry does not return true after this, the entry is in an undefined state.
*/
static inline void list_del(struct list_head *entry)
{
__list_del(entry->prev, entry->next);
entry->next = (struct list_head *) 0;
entry->prev = (struct list_head *) 0;
}
/**
* list_del_init - deletes entry from list and reinitialize it.
* @entry: the element to delete from the list.
*/
static inline void list_del_init(struct list_head *entry)
{
__list_del(entry->prev, entry->next);
INIT_LIST_HEAD(entry);
}
/**
* list_move - delete from one list and add as another's head
* @list: the entry to move
* @head: the head that will precede our entry
*/
static inline void list_move(struct list_head *list, struct list_head *head)
{
__list_del(list->prev, list->next);
list_add(list, head);
}
/**
* list_move_tail - delete from one list and add as another's tail
* @list: the entry to move
* @head: the head that will follow our entry
*/
static inline void list_move_tail(struct list_head *list,
struct list_head *head)
{
__list_del(list->prev, list->next);
list_add_tail(list, head);
}
/**
* list_empty - tests whether a list is empty
* @head: the list to test.
*/
static inline int list_empty(struct list_head *head)
{
return head->next == head;
}
static inline void __list_splice(struct list_head *list,
struct list_head *head)
{
struct list_head *first = list->next;
struct list_head *last = list->prev;
struct list_head *at = head->next;
first->prev = head;
head->next = first;
last->next = at;
at->prev = last;
}
/**
* list_splice - join two lists
* @list: the new list to add.
* @head: the place to add it in the first list.
*/
static inline void list_splice(struct list_head *list, struct list_head *head)
{
if (!list_empty(list))
__list_splice(list, head);
}
/**
* list_splice_init - join two lists and reinitialise the emptied list.
* @list: the new list to add.
* @head: the place to add it in the first list.
*
* The list at @list is reinitialised
*/
static inline void list_splice_init(struct list_head *list,
struct list_head *head)
{
if (!list_empty(list)) {
__list_splice(list, head);
INIT_LIST_HEAD(list);
}
}
/**
* list_entry - get the struct for this entry
* @ptr: the &struct list_head pointer.
* @type: the type of the struct this is embedded in.
* @member: the name of the list_struct within the struct.
*/
#define list_entry(ptr, type, member) \
((type *)((char *)(ptr)-(unsigned long)(&((type *)0)->member)))
/**
* list_first_entry - get the first element from a list
* @ptr: the list head to take the element from.
* @type: the type of the struct this is embedded in.
* @member: the name of the list_head within the struct.
*
* Note, that list is expected to be not empty.
*/
#define list_first_entry(ptr, type, member) \
list_entry((ptr)->next, type, member)
/**
* list_for_each - iterate over a list
* @pos: the &struct list_head to use as a loop counter.
* @head: the head for your list.
*/
#define list_for_each(pos, head) \
for (pos = (head)->next; pos != (head); \
pos = pos->next)
/**
* list_for_each_prev - iterate over a list backwards
* @pos: the &struct list_head to use as a loop counter.
* @head: the head for your list.
*/
#define list_for_each_prev(pos, head) \
for (pos = (head)->prev; pos != (head); \
pos = pos->prev)
/**
* list_for_each_safe - iterate over a list safe against removal of list entry
* @pos: the &struct list_head to use as a loop counter.
* @n: another &struct list_head to use as temporary storage
* @head: the head for your list.
*/
#define list_for_each_safe(pos, n, head) \
for (pos = (head)->next, n = pos->next; pos != (head); \
pos = n, n = pos->next)
/**
* list_for_each_entry - iterate over list of given type
* @pos: the type * to use as a loop counter.
* @head: the head for your list.
* @member: the name of the list_struct within the struct.
*/
#define list_for_each_entry(pos, head, member, type) \
for (pos = list_entry((head)->next, type, member); \
&pos->member != (head); \
pos = list_entry(pos->member.next, type, member))
/**
* list_for_each_entry_safe - iterate over list of given type safe against removal of list entry
* @pos: the type * to use as a loop counter.
* @n: another type * to use as temporary storage
* @head: the head for your list.
* @member: the name of the list_struct within the struct.
*/
#define list_for_each_entry_safe(pos, n, head, member, type) \
for (pos = list_entry((head)->next, type, member), \
n = list_entry(pos->member.next, type, member); \
&pos->member != (head); \
pos = n, n = list_entry(n->member.next, type, member))
#endif

View File

@@ -0,0 +1,337 @@
/**************************************************
* mktime/localtime wrap for gcc compiler
* port from newlib v3.2.0
**************************************************/
#if defined(__GNUC__)
#include <platform_stdlib.h>
#define SECSPERMIN 60L
#define MINSPERHOUR 60L
#define HOURSPERDAY 24L
#define SECSPERHOUR (SECSPERMIN * MINSPERHOUR)
#define SECSPERDAY (SECSPERHOUR * HOURSPERDAY)
#define DAYSPERWEEK 7
#define MONSPERYEAR 12
#define YEAR_BASE 1900
#define EPOCH_YEAR 1970
#define EPOCH_WDAY 4
#define EPOCH_YEARS_SINCE_LEAP 2
#define EPOCH_YEARS_SINCE_CENTURY 70
#define EPOCH_YEARS_SINCE_LEAP_CENTURY 370
#define isleap(y) ((((y) % 4) == 0 && ((y) % 100) != 0) || ((y) % 400) == 0)
#define EPOCH_ADJUSTMENT_DAYS 719468L
/* year to which the adjustment was made */
#define ADJUSTED_EPOCH_YEAR 0
/* 1st March of year 0 is Wednesday */
#define ADJUSTED_EPOCH_WDAY 3
/* there are 97 leap years in 400-year periods. ((400 - 97) * 365 + 97 * 366) */
#define DAYS_PER_ERA 146097L
/* there are 24 leap years in 100-year periods. ((100 - 24) * 365 + 24 * 366) */
#define DAYS_PER_CENTURY 36524L
/* there is one leap year every 4 years */
#define DAYS_PER_4_YEARS (3 * 365 + 366)
/* number of days in a non-leap year */
#define DAYS_PER_YEAR 365
/* number of days in January */
#define DAYS_IN_JANUARY 31
/* number of days in non-leap February */
#define DAYS_IN_FEBRUARY 28
/* number of years per era */
#define YEARS_PER_ERA 400
#define _SEC_IN_MINUTE 60L
#define _SEC_IN_HOUR 3600L
#define _SEC_IN_DAY 86400L
static const int DAYS_IN_MONTH[12] =
{31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
#define _DAYS_IN_MONTH(x) ((x == 1) ? days_in_feb : DAYS_IN_MONTH[x])
static const int _DAYS_BEFORE_MONTH[12] =
{0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334};
#define _ISLEAP(y) (((y) % 4) == 0 && (((y) % 100) != 0 || (((y)+1900) % 400) == 0))
#define _DAYS_IN_YEAR(year) (_ISLEAP(year) ? 366 : 365)
struct tm *
gmtime_r (const time_t *__restrict tim_p,
struct tm *__restrict res)
{
long days, rem;
const time_t lcltime = *tim_p;
int era, weekday, year;
unsigned erayear, yearday, month, day;
unsigned long eraday;
days = lcltime / SECSPERDAY + EPOCH_ADJUSTMENT_DAYS;
rem = lcltime % SECSPERDAY;
if (rem < 0)
{
rem += SECSPERDAY;
--days;
}
/* compute hour, min, and sec */
res->tm_hour = (int) (rem / SECSPERHOUR);
rem %= SECSPERHOUR;
res->tm_min = (int) (rem / SECSPERMIN);
res->tm_sec = (int) (rem % SECSPERMIN);
/* compute day of week */
if ((weekday = ((ADJUSTED_EPOCH_WDAY + days) % DAYSPERWEEK)) < 0)
weekday += DAYSPERWEEK;
res->tm_wday = weekday;
/* compute year, month, day & day of year */
/* for description of this algorithm see
* http://howardhinnant.github.io/date_algorithms.html#civil_from_days */
era = (days >= 0 ? days : days - (DAYS_PER_ERA - 1)) / DAYS_PER_ERA;
eraday = days - era * DAYS_PER_ERA; /* [0, 146096] */
erayear = (eraday - eraday / (DAYS_PER_4_YEARS - 1) + eraday / DAYS_PER_CENTURY -
eraday / (DAYS_PER_ERA - 1)) / 365; /* [0, 399] */
yearday = eraday - (DAYS_PER_YEAR * erayear + erayear / 4 - erayear / 100); /* [0, 365] */
month = (5 * yearday + 2) / 153; /* [0, 11] */
day = yearday - (153 * month + 2) / 5 + 1; /* [1, 31] */
month += month < 10 ? 2 : -10;
year = ADJUSTED_EPOCH_YEAR + erayear + era * YEARS_PER_ERA + (month <= 1);
res->tm_yday = yearday >= DAYS_PER_YEAR - DAYS_IN_JANUARY - DAYS_IN_FEBRUARY ?
yearday - (DAYS_PER_YEAR - DAYS_IN_JANUARY - DAYS_IN_FEBRUARY) :
yearday + DAYS_IN_JANUARY + DAYS_IN_FEBRUARY + isleap(erayear);
res->tm_year = year - YEAR_BASE;
res->tm_mon = month;
res->tm_mday = day;
res->tm_isdst = 0;
return (res);
}
struct tm * __wrap_localtime (const time_t * tim_p)
{
struct _reent *reent = _REENT;
_REENT_CHECK_TM(reent);
return gmtime_r (tim_p, (struct tm *)_REENT_TM(reent));
}
static void
validate_structure (struct tm *tim_p)
{
div_t res;
int days_in_feb = 28;
/* calculate time & date to account for out of range values */
if (tim_p->tm_sec < 0 || tim_p->tm_sec > 59)
{
res = div (tim_p->tm_sec, 60);
tim_p->tm_min += res.quot;
if ((tim_p->tm_sec = res.rem) < 0)
{
tim_p->tm_sec += 60;
--tim_p->tm_min;
}
}
if (tim_p->tm_min < 0 || tim_p->tm_min > 59)
{
res = div (tim_p->tm_min, 60);
tim_p->tm_hour += res.quot;
if ((tim_p->tm_min = res.rem) < 0)
{
tim_p->tm_min += 60;
--tim_p->tm_hour;
}
}
if (tim_p->tm_hour < 0 || tim_p->tm_hour > 23)
{
res = div (tim_p->tm_hour, 24);
tim_p->tm_mday += res.quot;
if ((tim_p->tm_hour = res.rem) < 0)
{
tim_p->tm_hour += 24;
--tim_p->tm_mday;
}
}
if (tim_p->tm_mon < 0 || tim_p->tm_mon > 11)
{
res = div (tim_p->tm_mon, 12);
tim_p->tm_year += res.quot;
if ((tim_p->tm_mon = res.rem) < 0)
{
tim_p->tm_mon += 12;
--tim_p->tm_year;
}
}
if (_DAYS_IN_YEAR (tim_p->tm_year) == 366)
days_in_feb = 29;
if (tim_p->tm_mday <= 0)
{
while (tim_p->tm_mday <= 0)
{
if (--tim_p->tm_mon == -1)
{
tim_p->tm_year--;
tim_p->tm_mon = 11;
days_in_feb =
((_DAYS_IN_YEAR (tim_p->tm_year) == 366) ?
29 : 28);
}
tim_p->tm_mday += _DAYS_IN_MONTH (tim_p->tm_mon);
}
}
else
{
while (tim_p->tm_mday > _DAYS_IN_MONTH (tim_p->tm_mon))
{
tim_p->tm_mday -= _DAYS_IN_MONTH (tim_p->tm_mon);
if (++tim_p->tm_mon == 12)
{
tim_p->tm_year++;
tim_p->tm_mon = 0;
days_in_feb =
((_DAYS_IN_YEAR (tim_p->tm_year) == 366) ?
29 : 28);
}
}
}
}
time_t __wrap_mktime (struct tm *tim_p)
{
time_t tim = 0;
long days = 0;
int year, isdst=0;
__tzinfo_type *tz = __gettzinfo ();
/* validate structure */
validate_structure (tim_p);
/* compute hours, minutes, seconds */
tim += tim_p->tm_sec + (tim_p->tm_min * _SEC_IN_MINUTE) +
(tim_p->tm_hour * _SEC_IN_HOUR);
/* compute days in year */
days += tim_p->tm_mday - 1;
days += _DAYS_BEFORE_MONTH[tim_p->tm_mon];
if (tim_p->tm_mon > 1 && _DAYS_IN_YEAR (tim_p->tm_year) == 366)
days++;
/* compute day of the year */
tim_p->tm_yday = days;
if (tim_p->tm_year > 10000 || tim_p->tm_year < -10000)
return (time_t) -1;
/* compute days in other years */
if ((year = tim_p->tm_year) > 70)
{
for (year = 70; year < tim_p->tm_year; year++)
days += _DAYS_IN_YEAR (year);
}
else if (year < 70)
{
for (year = 69; year > tim_p->tm_year; year--)
days -= _DAYS_IN_YEAR (year);
days -= _DAYS_IN_YEAR (year);
}
/* compute total seconds */
tim += (time_t)days * _SEC_IN_DAY;
if (_daylight)
{
int tm_isdst;
int y = tim_p->tm_year + YEAR_BASE;
/* Convert user positive into 1 */
tm_isdst = tim_p->tm_isdst > 0 ? 1 : tim_p->tm_isdst;
isdst = tm_isdst;
if (y == tz->__tzyear || __tzcalc_limits (y))
{
/* calculate start of dst in dst local time and
start of std in both std local time and dst local time */
time_t startdst_dst = tz->__tzrule[0].change
- (time_t) tz->__tzrule[1].offset;
time_t startstd_dst = tz->__tzrule[1].change
- (time_t) tz->__tzrule[1].offset;
time_t startstd_std = tz->__tzrule[1].change
- (time_t) tz->__tzrule[0].offset;
/* if the time is in the overlap between dst and std local times */
if (tim >= startstd_std && tim < startstd_dst)
; /* we let user decide or leave as -1 */
else
{
isdst = (tz->__tznorth
? (tim >= startdst_dst && tim < startstd_std)
: (tim >= startdst_dst || tim < startstd_std));
/* if user committed and was wrong, perform correction, but not
* if the user has given a negative value (which
* asks mktime() to determine if DST is in effect or not) */
if (tm_isdst >= 0 && (isdst ^ tm_isdst) == 1)
{
/* we either subtract or add the difference between
time zone offsets, depending on which way the user got it
wrong. The diff is typically one hour, or 3600 seconds,
and should fit in a 16-bit int, even though offset
is a long to accomodate 12 hours. */
int diff = (int) (tz->__tzrule[0].offset
- tz->__tzrule[1].offset);
if (!isdst)
diff = -diff;
tim_p->tm_sec += diff;
tim += diff; /* we also need to correct our current time calculation */
int mday = tim_p->tm_mday;
validate_structure (tim_p);
mday = tim_p->tm_mday - mday;
/* roll over occurred */
if (mday) {
/* compensate for month roll overs */
if (mday > 1)
mday = -1;
else if (mday < -1)
mday = 1;
/* update days for wday calculation */
days += mday;
/* handle yday */
if ((tim_p->tm_yday += mday) < 0) {
--year;
tim_p->tm_yday = _DAYS_IN_YEAR(year) - 1;
} else {
mday = _DAYS_IN_YEAR(year);
if (tim_p->tm_yday > (mday - 1))
tim_p->tm_yday -= mday;
}
}
}
}
}
}
/* add appropriate offset to put time in gmt format */
if (isdst == 1)
tim += (time_t) tz->__tzrule[1].offset;
else /* otherwise assume std time */
tim += (time_t) tz->__tzrule[0].offset;
/* reset isdst flag to what we have calculated */
tim_p->tm_isdst = isdst;
/* compute day of the week */
if ((tim_p->tm_wday = (days + 4) % 7) < 0)
tim_p->tm_wday += 7;
return tim;
}
#endif

View File

@@ -0,0 +1,265 @@
/******************************************************************************
*
* Copyright(c) 2007 - 2014 Realtek Corporation. All rights reserved.
*
*
******************************************************************************/
#ifndef __PLATFORM_STDLIB_H__
#define __PLATFORM_STDLIB_H__
#define USE_CLIB_PATCH 0
#if defined (__GNUC__)
/* build rom should set USE_RTL_ROM_CLIB=0 */
#include <rt_lib_rom.h>
#endif
#ifdef CONFIG_BUILD_ROM
#define USE_RTL_ROM_CLIB 0
#else
#define BUFFERED_PRINTF 0
#define USE_RTL_ROM_CLIB 1
#endif
#if defined(CONFIG_PLATFORM_8195A)
#if defined (__IARSTDLIB__)
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdint.h>
#include "diag.h"
#define strsep(str, delim) _strsep(str, delim)
#else
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "diag.h"
#include "strproc.h"
#include "basic_types.h"
#include "hal_misc.h"
#if USE_RTL_ROM_CLIB
#include "rtl_lib.h"
#endif
#undef printf
#undef sprintf
#undef snprintf
#undef atoi
#undef memcmp
#undef memcpy
#undef memset
#undef strcmp
#undef strcpy
#undef strlen
#undef strncmp
#undef strncpy
#undef strsep
#undef strtok
#if USE_RTL_ROM_CLIB
#undef memchr
#undef memmove
#undef strcat
#undef strchr
#undef strncat
#undef strstr
#endif
#if USE_RTL_ROM_CLIB
#if BUFFERED_PRINTF
extern int buffered_printf(const char* fmt, ...);
#define printf buffered_printf
#else
#define printf rtl_printf
#endif
#define sprintf rtl_sprintf
#define snprintf rtl_snprintf
#define memchr rtl_memchr
#define memcmp rtl_memcmp
#define memcpy rtl_memcpy
#define memmove rtl_memmove
#define memset rtl_memset
#define strcat rtl_strcat
#define strchr rtl_strchr
#define strcmp(s1, s2) rtl_strcmp((const char *)s1, (const char *)s2)
#define strcpy rtl_strcpy
#define strlen(str) rtl_strlen((const char *)str)
#define strncat rtl_strncat
#define strncmp(s1, s2, n) rtl_strncmp((const char *)s1, (const char *)s2, n)
#define strncpy rtl_strncpy
#define strstr rtl_strstr
#define strsep rtl_strsep
#define strtok rtl_strtok
#else
#if USE_CLIB_PATCH
extern int DiagSscanfPatch(const char *buf, const char *fmt, ...);
extern char* DiagStrtokPatch(char *str, const char* delim);
extern char* DiagStrstrPatch(char *string, char *substring);
extern int DiagSnPrintfPatch(char *buf, size_t size, const char *fmt, ...);
extern u32 DiagPrintfPatch(const char *fmt, ...);
extern u32 DiagSPrintfPatch(u8 *buf, const char *fmt, ...);
#define printf DiagPrintfPatch
#define sprintf DiagSPrintfPatch
#define snprintf DiagSnPrintfPatch
#define strstr(a, b) DiagStrstrPatch((char *)(a), (char *)(b))
#define strtok DiagStrtokPatch
#else
#define printf DiagPrintf
#define sprintf(fmt, arg...) DiagSPrintf((u8*)fmt, ##arg)
#if defined (__GNUC__)
#define snprintf DiagSnPrintf // NULL function
#define strstr(str1, str2) prvStrStr(str1, str2) // NULL function
#endif
#define strtok(str, delim) _strsep(str, delim)
#endif
#define memcmp(dst, src, sz) _memcmp(dst, src, sz)
#define memcpy(dst, src, sz) _memcpy(dst, src, sz)
#define memset(dst, val, sz) _memset(dst, val, sz)
#define strchr(s, c) _strchr(s, c) // for B-cut ROM
#define strcmp(str1, str2) prvStrCmp((const unsigned char *) str1, (const unsigned char *) str2)
#define strcpy(dest, src) _strcpy(dest, src)
#define strlen(str) prvStrLen((const unsigned char *) str)
#define strncmp(str1, str2, cnt) _strncmp(str1, str2, cnt)
#define strncpy(dest, src, count) _strncpy(dest, src, count)
#define strsep(str, delim) _strsep(str, delim)
#endif
#define atoi(str) prvAtoi(str)
#define strpbrk(cs, ct) _strpbrk(cs, ct) // for B-cut ROM
#if USE_CLIB_PATCH
#undef sscanf
#define sscanf DiagSscanfPatch
#else
#if defined (__GNUC__)
#undef sscanf //_sscanf
//extern int DiagSscanfPatch(const char *buf, const char *fmt, ...);
//#define sscanf DiagSscanfPatch
#define sscanf sscanf // use libc sscanf
#endif
#endif
#endif // defined (__IARSTDLIB__)
//
// memory management
//
extern void *pvPortMalloc( size_t xWantedSize );
extern void vPortFree( void *pv );
#define malloc pvPortMalloc
#define free vPortFree
#elif defined (CONFIG_PLATFORM_8711B)
#if defined (__IARSTDLIB__)
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdint.h>
#include <stdarg.h> /* va_list */
#include "diag.h"
#define strsep(str, delim) _strsep(str, delim)
#else
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdarg.h> /* va_list */
#include "diag.h"
#include "strproc.h"
#include "memproc.h"
#include "basic_types.h"
#if USE_RTL_ROM_CLIB
#include "rtl_lib.h"
#include "rom_libc_string.h"
#endif
#undef printf
#undef sprintf
#undef snprintf
#undef memchr
#undef memcmp
#undef memcpy
#undef memset
#undef memmove
#undef strcmp
#undef strcpy
#undef strlen
#undef strncmp
#undef strncpy
#undef strsep
#undef strtok
#undef strcat
#undef strchr
#undef strncat
#undef strstr
#undef atol
#undef atoi
#undef strpbrk
#if USE_RTL_ROM_CLIB
#if BUFFERED_PRINTF
extern int buffered_printf(const char* fmt, ...);
#define printf buffered_printf
#else
#define printf rtl_printf
#endif
#define sprintf rtl_sprintf
#define snprintf rtl_snprintf
#define vsnprintf rtl_vsnprintf
#else
#define printf DiagPrintf
#define sprintf(fmt, arg...) DiagSPrintf((u8*)fmt, ##arg)
#define snprintf DiagSnPrintf // NULL function
#define vsnprintf(buf, size, fmt, ap) VSprintf(buf, fmt, ap)
#endif
#define memchr __rtl_memchr_v1_00
#define memcmp(dst, src, sz) _memcmp(dst, src, sz)
#define memcpy(dst, src, sz) _memcpy(dst, src, sz)
#define memmove __rtl_memmove_v1_00
#define memset(dst, val, sz) _memset(dst, val, sz)
#define strchr(s, c) _strchr(s, c) // for B-cut ROM
#define strcmp(str1, str2) prvStrCmp((const unsigned char *) str1, (const unsigned char *) str2)
#define strcpy(dest, src) _strcpy(dest, src)
#define strlen(str) prvStrLen((const unsigned char *) str)
#define strsep(str, delim) _strsep(str, delim)
#define strstr(str1, str2) prvStrStr(str1, str2) // NULL function
#define strtok(str, delim) prvStrtok(str, delim)//_strsep(str, delim)
#define strcat __rtl_strcat_v1_00
#define strncmp(str1, str2, cnt) _strncmp(str1, str2, cnt)
#define strncpy(dest, src, count) _strncpy(dest, src, count)
#define strncat __rtl_strncat_v1_00
#define atol(str) strtol(str,NULL,10)
#define atoi(str) prvAtoi(str)
#define strpbrk(cs, ct) _strpbrk(cs, ct) // for B-cut ROM
#if defined (__GNUC__)
#undef sscanf
#define sscanf _sscanf_patch
#define rand Rand
#endif
//extern int _sscanf_patch(const char *buf, const char *fmt, ...);
//#define sscanf _sscanf_patch
#endif // defined (__IARSTDLIB__)
//
// memory management
//
extern void *pvPortMalloc( size_t xWantedSize );
extern void vPortFree( void *pv );
extern void* pvPortReAlloc( void *pv, size_t xWantedSize );
#define malloc pvPortMalloc
#define free vPortFree
#define realloc pvPortReAlloc
#elif defined(USE_STM322xG_EVAL) || defined(USE_STM324xG_EVAL) || defined(STM32F10X_XL)
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdint.h>
#endif
#endif //__PLATFORM_STDLIB_H__

View File

@@ -0,0 +1,918 @@
/*
this is the c lib patch, It can help when the clib provided by IAR
does not work well.
How to use this:
1.You must include platform_stdlib.h in you source file。
2.There is a macro USE_CLIB_PATCH in platform_stdlib.h should be opened.
If there is some problems using this patch,
You'd better check if you code runs into these functions:
DiagSscanfPatch
DiagStrtokPatch
DiagStrstrPatch
DiagSnPrintfPatch
DiagPrintfPatch
DiagSPrintfPatch
DiagPrintfPatch
DiagSPrintfPatch
DiagSnPrintfPatch
DiagStrstrPatch
DiagStrtokPatch
*/
#ifndef CONFIG_PLATFORM_8711B
#include <stdarg.h>
#define DiagPutChar HalSerialPutcRtl8195a
#define IN
#define NULL 0
typedef unsigned int size_t;
typedef unsigned int SIZE_T;
typedef unsigned long long u64;
typedef unsigned int u32;
typedef unsigned short int u16;
typedef unsigned char u8;
typedef signed long long s64;
typedef signed int s32;
typedef signed short int s16;
typedef unsigned char bool;
#define in_range(c, lo, up) ((u8)c >= lo && (u8)c <= up)
#define isprint(c) in_range(c, 0x20, 0x7f)
#define isdigit(c) in_range(c, '0', '9')
#define isxdigit(c) (isdigit(c) || in_range(c, 'a', 'f') || in_range(c, 'A', 'F'))
#define islower(c) in_range(c, 'a', 'z')
#define isspace(c) (c == ' ' || c == '\f' || c == '\n' || c == '\r' || c == '\t' || c == '\v' || c == ',')
#define ULLONG_MAX (~0ULL)
#define USHRT_MAX ((u16)(~0U))
#define KSTRTOX_OVERFLOW (1U << 31)
#define SHRT_MAX ((s16)(USHRT_MAX>>1))
static inline char _tolower(const char c)
{
return c | 0x20;
}
extern s64 div_s64_rem(s64 dividend, s32 divisor, s32 *remainder);
extern s64 div_s64(s64 dividend, s32 divisor);
extern inline char _tolower(const char c);
extern u64 div_u64_rem(u64 dividend, u32 divisor, u32 *remainder);
extern u64 div_u64(u64 dividend, u32 divisor);
extern unsigned int _parse_integer(const char *s, unsigned int base, unsigned long long *p);
extern const char *_parse_integer_fixup_radix(const char *s, unsigned int *base);
extern char *skip_spaces(const char *str);
extern int skip_atoi(const char **s);
extern void HalSerialPutcRtl8195a(u8 c);
static unsigned long long simple_strtoull_patch(const char *cp, char **endp, unsigned int base)
{
unsigned long long result;
unsigned int rv;
cp = _parse_integer_fixup_radix(cp, &base);
rv = _parse_integer(cp, base, &result);
return result;
}
static long long simple_strtoll_patch(const char *cp, char **endp, unsigned int base)
{
if(*cp == '-')
return -simple_strtoull_patch(cp + 1, endp, base);
return simple_strtoull_patch(cp, endp, base);
}
static unsigned long simple_strtoul_patch(const char *cp, char **endp, unsigned int base)
{
return simple_strtoull_patch(cp, endp, base);
}
static long simple_strtol_patch(const char *cp, char **endp, unsigned int base)
{
if(*cp == '-')
return -simple_strtoul_patch(cp + 1, endp, base);
return simple_strtoul_patch(cp, endp, base);
}
static int judge_digit_width(const char *str)
{
int width = 0;
while(isdigit(*str)) {
width++;
str++;
}
return width;
}
static int _vsscanf_patch(const char *buf, const char *fmt, va_list args)
{
const char *str = buf;
char *next;
char digit;
int num = 0;
int i =0;
u8 qualifier;
unsigned int base;
union {
long long s;
unsigned long long u;
} val;
s16 field_width;
bool is_sign;
char str_store[20] = {0};
while(*fmt) {
/* skip any white space in format */
/* white space in format matchs any amount of
* white space, including none, in the input.
*/
if(isspace(*fmt)) {
fmt = skip_spaces(++fmt);
str = skip_spaces(str);
}
/* anything that is not a conversion must match exactly */
if(*fmt != '%' && *fmt) {
if(*fmt++ != *str++) {
break;
}
continue;
}
if(!*fmt) {
break;
}
++fmt;
/* skip this conversion.
* advance both strings to next white space
*/
if(*fmt == '*') {
if(!*str) {
break;
}
while(!isspace(*fmt) && *fmt != '%' && *fmt)
fmt++;
while(!isspace(*str) && *str)
str++;
continue;
}
/* get field width */
field_width = -1;
if(isdigit(*fmt)) {
field_width = skip_atoi(&fmt);
if(field_width <= 0) {
break;
}
}
/* get conversion qualifier */
qualifier = -1;
if(*fmt == 'h' || _tolower(*fmt) == 'l' ||
_tolower(*fmt) == 'z') {
qualifier = *fmt++;
if(qualifier == *fmt) {
if(qualifier == 'h') {
qualifier = 'H';
fmt++;
} else if(qualifier == 'l') {
qualifier = 'L';
fmt++;
}
}
}
if(!*fmt) {
break;
}
if(*fmt == 'n') {
/* return number of characters read so far */
*va_arg(args, int *) = str - buf;
++fmt;
continue;
}
if(!*str) {
break;
}
base = 10;
is_sign = 0;
switch(*fmt++) {
case 'c': {
char *s = (char *)va_arg(args, char*);
if(field_width == -1)
field_width = 1;
do {
*s++ = *str++;
} while(--field_width > 0 && *str);
num++;
}
continue;
case 's': {
char *s = (char *)va_arg(args, char *);
if(field_width == -1)
field_width = SHRT_MAX;
/* first, skip leading white space in buffer */
str = skip_spaces(str);
/* now copy until next white space */
while(*str && !isspace(*str) && field_width--) {
*s++ = *str++;
}
*s = '\0';
num++;
}
continue;
case 'o':
base = 8;
break;
case 'x':
case 'X':
base = 16;
break;
case 'i':
base = 0;
case 'd':
is_sign = 1;
case 'u':
break;
case '%':
/* looking for '%' in str */
if(*str++ != '%') {
return num;
}
continue;
default:
/* invalid format; stop here */
return num;
}
/* have some sort of integer conversion.
* first, skip white space in buffer.
*/
str = skip_spaces(str);
digit = *str;
if(is_sign && digit == '-')
digit = *(str + 1);
if(!digit
|| (base == 16 && !isxdigit(digit))
|| (base == 10 && !isdigit(digit))
|| (base == 8 && (!isdigit(digit) || digit > '7'))
|| (base == 0 && !isdigit(digit))) {
break;
}
//here problem *******************************************
//troy add ,fix support %2d, but not support %d
if(field_width <= 0) {
field_width = judge_digit_width(str);
}
/////troy add, fix str passed inwidth wrong
for(i = 0; i<field_width ; i++)
str_store[i] = str[i];
next = (char*)str + field_width;
if(is_sign) {
val.s = qualifier != 'L' ?
simple_strtol_patch(str_store, &next, base) :
simple_strtoll_patch(str_store, &next, base);
} else {
val.u = qualifier != 'L' ?
simple_strtoul_patch(str_store, &next, base) :
simple_strtoull_patch(str_store, &next, base);
}
////troy add
for(i = 0; i<20 ; i++)
str_store[i] = 0;
//判断转换的字符串的宽度是否大于 %2d
if(field_width > 0 && next - str > field_width) {
if(base == 0)
_parse_integer_fixup_radix(str, &base);
while(next - str > field_width) {
if(is_sign) {
val.s = div_s64(val.s, base);
} else {
val.u = div_u64(val.u, base);
}
--next;
}
}
switch(qualifier) {
case 'H': /* that's 'hh' in format */
if(is_sign)
*va_arg(args, signed char *) = val.s;
else
*va_arg(args, unsigned char *) = val.u;
break;
case 'h':
if(is_sign)
*va_arg(args, short *) = val.s;
else
*va_arg(args, unsigned short *) = val.u;
break;
case 'l':
if(is_sign)
*va_arg(args, long *) = val.s;
else
*va_arg(args, unsigned long *) = val.u;
break;
case 'L':
if(is_sign)
*va_arg(args, long long *) = val.s;
else
*va_arg(args, unsigned long long *) = val.u;
break;
case 'Z':
case 'z':
*va_arg(args, size_t *) = val.u;
break;
default:
if(is_sign)
*va_arg(args, int *) = val.s;
else
*va_arg(args, unsigned int *) = val.u;
break;
}
num++;
if(!next) {
break;
}
str = next;
}
return num;
}
int DiagSscanfPatch(const char *buf, const char *fmt, ...)
{
va_list args;
int i;
va_start(args, fmt);
i = _vsscanf_patch(buf, fmt, args);
va_end(args);
return i;
}
/*********************************************************/
char* DiagStrtokPatch(char *str, const char* delim) {
static char* _buffer;
if(str != NULL) _buffer = str;
if(_buffer[0] == '\0') return NULL;
char *ret = _buffer, *b;
const char *d;
for(b = _buffer; *b !='\0'; b++) {
for(d = delim; *d != '\0'; d++) {
if(*b == *d) {
*b = '\0';
_buffer = b+1;
// skip the beginning delimiters
if(b == ret) {
ret++;
continue;
}
return ret;
}
}
}
return ret;
}
/*********************************************************/
char *DiagStrstrPatch(char *string, char *substring)
{
register char *a, *b;
/* First scan quickly through the two strings looking for a
* single-character match. When it's found, then compare the
* rest of the substring.
*/
b = substring;
if(*b == 0) {
return string;
}
for(; *string != 0; string += 1) {
if(*string != *b) {
continue;
}
a = string;
while(1) {
if(*b == 0) {
return string;
}
if(*a++ != *b++) {
break;
}
}
b = substring;
}
return (char *) 0;
}
/*********************************************************/
int DiagSnPrintfPatch(char *buf, size_t size, const char *fmt, ...)
{
va_list ap;
char *p, *s, *buf_end = NULL;
const int *dp = ((const int *)&fmt)+1;
if(buf == NULL)
return 0;
va_start(ap, fmt);
s = buf;
buf_end = size? (buf + size):(char*)~0;
for(; *fmt != '\0'; ++fmt) {
if(*fmt != '%') {
*s++ = *fmt;
if(s >= buf_end) {
goto Exit;
}
continue;
}
if(*++fmt == 's') {
for(p = (char *)*dp++; *p != '\0'; p++) {
*s++ = *p;
if(s >= buf_end) {
goto Exit;
}
}
}
else { /* Length of item is bounded */
char tmp[20], *q = tmp;
int alt = 0;
int shift = 0;// = 12;
const long *lpforchk = (const long *)dp;
if((*lpforchk) < 0x10) {
shift = 0;
}
else if(((*lpforchk) >= 0x10) && ((*lpforchk) < 0x100)) {
shift = 4;
}
else if(((*lpforchk) >= 0x100) && ((*lpforchk) < 0x1000)) {
shift = 8;
}
else if(((*lpforchk) >= 0x1000) && ((*lpforchk) < 0x10000)) {
shift = 12;
}
else if(((*lpforchk) >= 0x10000) && ((*lpforchk) < 0x100000)) {
shift = 16;
}
else if(((*lpforchk) >= 0x100000) && ((*lpforchk) < 0x1000000)) {
shift = 20;
}
else if(((*lpforchk) >= 0x1000000) && ((*lpforchk) < 0x10000000)) {
shift = 24;
}
else if((*lpforchk) >= 0x10000000) {
shift = 28;
}
else {
shift = 28;
}
if((*fmt >= '0') && (*fmt <= '9'))
{
int width;
unsigned char fch = *fmt;
for(width=0; (fch>='0') && (fch<='9'); fch=*++fmt)
{ width = width * 10 + fch - '0';
}
shift=(width-1)*4;
}
/*
* Before each format q points to tmp buffer
* After each format q points past end of item
*/
if((*fmt == 'x')||(*fmt == 'X') || (*fmt == 'p') || (*fmt == 'P')) {
/* With x86 gcc, sizeof(long) == sizeof(int) */
const long *lp = (const long *)dp;
long h = *lp++;
int hex_count = 0;
unsigned long h_back = h;
int ncase = (*fmt & 0x20);
dp = (const int *)lp;
if((*fmt == 'p') || (*fmt == 'P'))
alt=1;
if(alt) {
*q++ = '0';
*q++ = 'X' | ncase;
}
while(h_back) {
hex_count += (h_back & 0xF) ? 1 : 0;
h_back = h_back >> 4;
}
if(shift < (hex_count - 1)*4)
shift = (hex_count - 1)*4;
for(; shift >= 0; shift -= 4)
*q++ = "0123456789ABCDEF"[(h >> shift) & 0xF] | ncase;
}
else if(*fmt == 'd') {
int i = *dp++;
char *r;
int digit_space = 0;
if(i < 0) {
*q++ = '-';
i = -i;
digit_space++;
}
p = q; /* save beginning of digits */
do {
*q++ = '0' + (i % 10);
i /= 10;
digit_space++;
} while(i);
for(; shift >= 0; shift -= 4) {
if(digit_space-- > 0) {
; //do nothing
} else {
*q++ = '0';
}
}
/* reverse digits, stop in middle */
r = q; /* don't alter q */
while(--r > p) {
i = *r;
*r = *p;
*p++ = i;
}
}
else if(*fmt == 'c')
*q++ = *dp++;
else
*q++ = *fmt;
/* now output the saved string */
for(p = tmp; p < q; ++p) {
*s++ = *p;
if(s >= buf_end) {
goto Exit;
}
}
}
}
Exit:
if(buf)
*s = '\0';
va_end(ap);
return(s-buf);
}
/*********************************************************/
static int VSprintfPatch(char *buf, const char *fmt, const int *dp)
{
char *p, *s;
s = buf;
for(; *fmt != '\0'; ++fmt) {
if(*fmt != '%') {
if(buf) {
*s++ = *fmt;
} else {
DiagPutChar(*fmt);
}
continue;
}
if(*++fmt == 's') {
for(p = (char *)*dp++; *p != '\0'; p++) {
if(buf) {
*s++ = *p;
} else {
DiagPutChar(*p);
}
}
}
else { /* Length of item is bounded */
char tmp[20], *q = tmp;
int alt = 0;
int shift = 0;// = 12;
const long *lpforchk = (const long *)dp;
if((*lpforchk) < 0x10) {
shift = 0;
}
else if(((*lpforchk) >= 0x10) && ((*lpforchk) < 0x100)) {
shift = 4;
}
else if(((*lpforchk) >= 0x100) && ((*lpforchk) < 0x1000)) {
shift = 8;
}
else if(((*lpforchk) >= 0x1000) && ((*lpforchk) < 0x10000)) {
shift = 12;
}
else if(((*lpforchk) >= 0x10000) && ((*lpforchk) < 0x100000)) {
shift = 16;
}
else if(((*lpforchk) >= 0x100000) && ((*lpforchk) < 0x1000000)) {
shift = 20;
}
else if(((*lpforchk) >= 0x1000000) && ((*lpforchk) < 0x10000000)) {
shift = 24;
}
else if((*lpforchk) >= 0x10000000) {
shift = 28;
}
else {
shift = 28;
}
#if 1 //wei patch for %02x
if((*fmt >= '0') && (*fmt <= '9'))
{
int width;
unsigned char fch = *fmt;
for(width=0; (fch>='0') && (fch<='9'); fch=*++fmt)
{ width = width * 10 + fch - '0';
}
shift=(width-1)*4;
}
#endif
/*
* Before each format q points to tmp buffer
* After each format q points past end of item
*/
if((*fmt == 'x')||(*fmt == 'X') || (*fmt == 'p') || (*fmt == 'P')) {
/* With x86 gcc, sizeof(long) == sizeof(int) */
const long *lp = (const long *)dp;
long h = *lp++;
int hex_count = 0;
unsigned long h_back = h;
int ncase = (*fmt & 0x20);
dp = (const int *)lp;
if((*fmt == 'p') || (*fmt == 'P'))
alt=1;
if(alt) {
*q++ = '0';
*q++ = 'X' | ncase;
}
//hback 是实际得到的数据hex_count是统计数据的HEX字符个数
while(h_back) {
hex_count += (h_back & 0xF) ? 1 : 0;
h_back = h_back >> 4;
}
//这里修复 example 字符有4个但是用了%02x导致字符被截断的情况
if(shift < (hex_count - 1)*4)
shift = (hex_count - 1)*4;
//printf("(%d,%d)", hex_count, shift);
for(; shift >= 0; shift -= 4) {
*q++ = "0123456789ABCDEF"[(h >> shift) & 0xF] | ncase;
}
}
else if(*fmt == 'd') {
int i = *dp++;
char *r;
int digit_space = 0;
if(i < 0) {
*q++ = '-';
i = -i;
digit_space++;
}
p = q; /* save beginning of digits */
do {
*q++ = '0' + (i % 10);
i /= 10;
digit_space++;
} while(i);
//这里修复 example用了%08d后在数字前面没有0的情况
for(; shift >= 0; shift -= 4) {
if(digit_space-- > 0) {
; //do nothing
} else {
*q++ = '0';
}
}
/* reverse digits, stop in middle */
r = q; /* don't alter q */
while(--r > p) {
i = *r;
*r = *p;
*p++ = i;
}
}
else if(*fmt == 'c')
*q++ = *dp++;
else
*q++ = *fmt;
/* now output the saved string */
for(p = tmp; p < q; ++p) {
if(buf) {
*s++ = *p;
} else {
DiagPutChar(*p);
}
if((*p) == '\n') {
DiagPutChar('\r');
}
}
}
}
if(buf)
*s = '\0';
return (s - buf);
}
u32 DiagPrintfPatch(
IN const char *fmt, ...
)
{
(void)VSprintfPatch(0, fmt, ((const int *)&fmt)+1);
return 1;
}
u32 DiagSPrintfPatch(
IN u8 *buf,
IN const char *fmt, ...
)
{
(void)VSprintfPatch((char*)buf, fmt, ((const int *)&fmt)+1);
return 1;
}
#endif

View File

@@ -0,0 +1,7 @@
#ifndef _TIME_64_GCC_H
#define _TIME_64_GCC_H
#define __time_t_defined
#define time_t long long
#endif //_TIME_64_GCC_H

View File

@@ -0,0 +1,149 @@
#include <PinNames.h>
#include <pinmap.h>
#include <gpio_api.h>
#include <wifi_wowlan.h>
#include <freertos_pmu.h>
#include <wifi_conf.h>
#define CONFIG_WOWLAN_DEV_NT96658 //build for Nova NT96658
//#define CONFIG_WOWLAN_DEV_OV788 //build for OmniVision OV788
#if defined(CONFIG_WOWLAN_DEV_NT96658) && defined(CONFIG_WOWLAN_DEV_OV788)
#error "CONFIG_WOWLAN_DEV_NT96658 and CONFIG_WOWLAN_DEV_OV788 are mutually exclusive. "
#endif
#ifdef CONFIG_WOWLAN_DEV_NT96658
#define WOW_WIFI_IN_PIN PE_4 //JTAG pin, so JTAG must be disable before using this pin as wakeup pin
#define WOW_TRIGGER_INTERVAL 500
#elif defined(CONFIG_WOWLAN_DEV_OV788)
#define WOW_WIFI_IN_PIN PD_5
#define WOW_WLAN_ON_PIN PB_3
#define WOW_TRIGGER_INTERVAL 200
#else
#error "Either CONFIG_WOWLAN_DEV_NT96658 or CONFIG_WOWLAN_DEV_OV788 should be defined, but not both. "
#endif
//pin assignment for SDIO, default pull high
#define SD_D2 PA_0
#define SD_D3 PA_1
#define SD_CMD PA_2
#define SD_CLK PA_3
#define SD_D0 PA_4
#define SD_D1 PA_5
#define SD_CD PA_6
gpio_t wow_gpio_wifi_in; //WOWLAN WAKEUP TRIGGER PORT
gpio_t wow_gpio_wlan_on; //RECORD WOWLAN STATUS: 1:OFF, 0:ON
int dev_wowlan_init(void){
WOWLAN_PRINTK("WOWLAN: device init!");
#ifdef CONFIG_WOWLAN_DEV_OV788
// Initial WLAN_ON pin
gpio_init(&wow_gpio_wlan_on, WOW_WLAN_ON_PIN);
gpio_dir(&wow_gpio_wlan_on, PIN_OUTPUT);
gpio_mode(&wow_gpio_wlan_on, PullNone);
gpio_write(&wow_gpio_wlan_on, 1);
#endif
return 0;
}
int dev_wowlan_enable(void){
WOWLAN_PRINTK("WOWLAN: device enable!");
// Init WIFI_IN pin (wakeup pin)
gpio_init(&wow_gpio_wifi_in, WOW_WIFI_IN_PIN);
gpio_dir(&wow_gpio_wifi_in, PIN_OUTPUT);
gpio_mode(&wow_gpio_wifi_in, PullNone);
gpio_write(&wow_gpio_wifi_in, 0);
#ifdef CONFIG_WOWLAN_DEV_OV788
gpio_write(&wow_gpio_wlan_on, 0);
#endif
#if CONFIG_WLAN
wifi_set_power_mode(0xff, 1);
#endif
return 0;
}
int dev_wowlan_wakeup_process(void){
WOWLAN_PRINTK("WOWLAN: device wake up!");
#if defined(CONFIG_WOWLAN_DEV_NT96658) || defined(CONFIG_WOWLAN_DEV_OV788)
#if defined(configUSE_WAKELOCK_PMU) && (configUSE_WAKELOCK_PMU == 1)
//acquire wakelock to keep system awake
pmu_acquire_wakelock(PMU_SDIO_DEVICE);
#endif
#endif
#ifdef CONFIG_WOWLAN_DEV_OV788
//record wowlan status
gpio_write(&wow_gpio_wlan_on, 1);
#endif
#if defined(CONFIG_WOWLAN_DEV_NT96658)
//restore SDIO pin status for bus communication
pin_mode(SD_D0, PullUp);
pin_mode(SD_D1, PullUp);
pin_mode(SD_D2, PullUp);
pin_mode(SD_D3, PullUp);
pin_mode(SD_CMD, PullUp);
pin_mode(SD_CLK, PullDown);
#endif
//send signal to awake host
gpio_write(&wow_gpio_wifi_in, 0);
wowlan_mdelay_os(WOW_TRIGGER_INTERVAL);
gpio_write(&wow_gpio_wifi_in, 1);
wowlan_mdelay_os(WOW_TRIGGER_INTERVAL);
gpio_write(&wow_gpio_wifi_in, 0);
wowlan_mdelay_os(WOW_TRIGGER_INTERVAL);
return 0;
}
int dev_wowlan_sleep_process(void){
#if defined(CONFIG_WOWLAN_DEV_NT96658)
//pull control for SDIO pin only when host is already power off
if(rtw_wowlan_is_enabled() && (rtw_wowlan_get_wk_reason() == 0)){
WOWLAN_PRINTK("pull control");
//configure SDIO pin status for avoiding current leakage
pin_mode(SD_D0, PullNone);
pin_mode(SD_D1, PullNone);
pin_mode(SD_D2, PullNone);
pin_mode(SD_D3, PullNone);
pin_mode(SD_CMD, PullNone);
pin_mode(SD_CLK, PullNone);
}
#endif
return 0;
}
int dev_wowlan_disable(void){
WOWLAN_PRINTK("WOWLAN: device disable!");
#if CONFIG_WLAN
wifi_set_power_mode(0xff, 0);
#endif
#ifdef CONFIG_WOWLAN_DEV_OV788
gpio_write(&wow_gpio_wlan_on, 1);
#endif
return 0;
}
void dev_wowlan_ops_init(void *dev_ops){
struct rtw_wowlan_ops *ops = (struct rtw_wowlan_ops *)dev_ops;
WOWLAN_PRINTK("WOWLAN: device ops init!");
ops->DevWowlanInit = dev_wowlan_init;
ops->DevWowlanEnable = dev_wowlan_enable;
ops->DevWowlanDisable = dev_wowlan_disable;
ops->DevWowlanWakeUp = dev_wowlan_wakeup_process;
ops->DevWowlanSleep = dev_wowlan_sleep_process;
}

View File

@@ -0,0 +1,385 @@
#ifndef _WIFI_WOWLAN_H_
#define _WIFI_WOWLAN_H_
#include <platform_stdlib.h>
#include <osdep_service.h>
#define WOWLAN_DBG 1
enum{
WOWLAN_DBG_OFF = 0,
WOWLAN_DBG_ALWAYS,
WOWLAN_DBG_ERROR,
WOWLAN_DBG_WARNING,
WOWLAN_DBG_INFO
};
#if WOWLAN_DBG
//#define WOWLAN_DUMP_MSG
#define WOWLAN_DUMP_MSG_1 //dump packet when setting
static unsigned char gWowlanDbgLevel = WOWLAN_DBG_ERROR;
#define WOWLAN_PRINTK(fmt, args...) printf(fmt"\r\n",## args)
#define _WOWLAN_PRINTK(fmt, args...) printf(fmt,## args)
#define WOWLAN_DBG_MSG(level, fmt, args...) \
do{ \
if(level <= gWowlanDbgLevel){ \
WOWLAN_PRINTK(fmt,## args); \
} \
}while(0)
#else
#define WOWLAN_PRINTK(fmt, args...)
#define WOWLAN_DBG_MSG(level, fmt, args...)
#endif
#ifndef u8
typedef unsigned char u8;
typedef unsigned short u16;
typedef unsigned int u32;
#endif
#ifndef BIT
#define BIT(x) ((u32)1 << (x))
#endif
#ifndef le16_to_cpu //need a general definition for the whole system
#define cpu_to_le32(x) ((u32)(x))
#define le32_to_cpu(x) ((u32)(x))
#define cpu_to_le16(x) ((u16)(x))
#define le16_to_cpu(x) ((u16)(x))
#endif
#ifndef IP_FMT
#define IP_FMT "%d.%d.%d.%d"
#endif
#ifndef IP_ARG
#define IP_ARG(x) ((u8*)(x))[0],((u8*)(x))[1],((u8*)(x))[2],((u8*)(x))[3]
#endif
#ifndef MAC_FMT
#define MAC_FMT "%02x:%02x:%02x:%02x:%02x:%02x"
#endif
#ifndef MAC_ARG
#define MAC_ARG(x) ((u8*)(x))[0],((u8*)(x))[1],((u8*)(x))[2],((u8*)(x))[3],((u8*)(x))[4],((u8*)(x))[5]
#endif
#ifndef ETH_ALEN
#define ETH_ALEN 6
#endif
#ifndef ethhdr
struct ethhdr
{
unsigned char h_dest[ETH_ALEN]; /* destination eth addr */
unsigned char h_source[ETH_ALEN]; /* source ether addr */
unsigned short h_proto; /* packet type ID field */
};
#endif
#ifndef wowlan_memcpy
#define wowlan_memcpy(d, s, n) rtw_memcpy((void*)(d), ((void*)(s)), (n))
#endif
#ifndef wowlan_malloc
#define wowlan_malloc(sz) rtw_malloc(sz)
#endif
#ifndef wowlan_zmalloc
#define wowlan_zmalloc(sz) rtw_zmalloc(sz)
#endif
#ifndef wowlan_memset
#define wowlan_memset(pbuf, c, sz) rtw_memset(pbuf, c, sz)
#endif
#ifndef wowlan_mfree
#define wowlan_mfree(p, sz) rtw_mfree(((u8*)(p)), (sz))
#endif
#ifndef wowlan_memcmp
#define wowlan_memcmp(s1, s2, n) rtw_memcmp(((void*)(s1)), ((void*)(s2)), (n))
#endif
#ifndef wowlan_mdelay_os
#define wowlan_mdelay_os(ms) rtw_mdelay_os(ms)
#endif
/*Mutex services*/
typedef _mutex _wowlock;
__inline static void _init_wowlock(_wowlock *plock)
{
rtw_mutex_init(plock);
}
__inline static void _free_wowlock(_wowlock *plock)
{
rtw_mutex_free(plock);
}
__inline static void _enter_wowlock(_wowlock *plock)
{
rtw_mutex_get(plock);
}
__inline static void _exit_wowlock(_wowlock *plock)
{
rtw_mutex_put(plock);
}
/*Timer services*/
typedef _timerHandle _wowTimer;
#define TMR_AUTO_RELOAD_EN _TRUE
#define TMR_AUTO_RELOAD_DIS _FALSE
__inline static void
_wowlan_init_timer(_wowTimer *ptimer, void *adapter, TIMER_FUN pfunc,void* cntx, const char *name, u32 auto_reload)
{
*ptimer = rtw_timerCreate(
(signed const char *)name, // Just a text name, not used by the RTOS kernel.
TIMER_MAX_DELAY, // Timer Period, not 0
auto_reload, // Whether timer will auto-load themselves when expires
cntx, // Uniq id used to identify which timer expire..
pfunc // Timer callback
);
}
__inline static void
_wowlan_set_timer(_wowTimer *ptimer, u32 delay_time_ms)
{
if(rtw_timerChangePeriod(*ptimer, rtw_ms_to_systime(delay_time_ms), TIMER_MAX_DELAY) == _FAIL)
WOWLAN_PRINTK("Fail to set timer period");
}
__inline static void
_wowlan_cancel_timer(_wowTimer *ptimer)
{
rtw_timerStop(*ptimer, TIMER_MAX_DELAY);
}
__inline static void
_wowlan_del_timer(_wowTimer *ptimer)
{
rtw_timerDelete(*ptimer, TIMER_MAX_DELAY);
}
__inline static void *
_wowlan_get_timer_cntx(_wowTimer timer)
{
#ifdef PLATFORM_FREERTOS
#include <FreeRTOS.h>
#include <timers.h>
return pvTimerGetTimerID(timer);
#else
#error "_wowlan_get_timer_cntx is not defined"
#endif
}
enum rtw_wowlan_wakeup_reason {
RTW_WOWLAN_WAKEUP_BY_PATTERN = BIT(0),
RTW_WOWLAN_WAKEUP_BY_DISCONNECTION = BIT(1),
RTW_WOWLAN_WAKEUP_MAX = 0x7FFFFFFF
};
enum rtw_wowlan_cmd_id{
RTW_WOWLAN_CMD_ENABLE = 0x01, // enable wowlan service
RTW_WOWLAN_CMD_PATTERNS = 0x02, // wowlan pattern setting
RTW_WOWLAN_CMD_PROT_OFFLOAD_CONFIG = 0x03, //ARP offload setting
RTW_WOWLAN_CMD_GET_STATUS = 0x04, // get rtw_wowlan_status
RTW_WOWLAN_CMD_CLEAR_ALL = 0x05, //clear wowlan content
RTW_WOWLAN_CMD_KEEPALIVE = 0x06, //for keep alive packet setting
RTW_WOWLAN_CMD_MAX = 0xff
};
#define RTW_WOWLAN_MAX_RX_FILTERS (5)
#define RTW_WOWLAN_RX_FILTER_MAX_FIELDS (8)
#define RTW_WOWLAN_ID_OFFSET (100) //to match some application, ID starts from 100
#define RTW_WOWLAN_MIN_FILTERS_ID (RTW_WOWLAN_ID_OFFSET)
#define RTW_WOWLAN_MAX_FILTERS_ID (RTW_WOWLAN_ID_OFFSET+RTW_WOWLAN_MAX_RX_FILTERS-1)
struct rtw_wowlan_rx_filter_field {
u16 offset;
u8 len;
u8 flags;
u8 *mask;
u8 *pattern;
};
struct rtw_wowlan_rx_filter {
u8 action;
u8 offset;
u8 num_fields;
struct rtw_wowlan_rx_filter_field fields[RTW_WOWLAN_RX_FILTER_MAX_FIELDS];
};
#if defined(__IAR_SYSTEMS_ICC__)|| defined (__GNUC__)
#pragma pack(1)
#else
#error "this structure needs to be packed!"
#endif
struct rtw_wowlan_status {
u32 wakeup_reasons; //record wake up reason
u32 filter_id; //record which pattern is matched
};
#if defined(__IAR_SYSTEMS_ICC__)|| defined (__GNUC__)
#pragma pack()
#else
#error "this structure needs to be packed!"
#endif
/**
* struct rtw_wowlan_keepalive_packet
*
* @payload_len: data payload length
* @payload: data payload buffer
* @data_interval: interval at which to send data packets
**/
#define RTW_WOWLAN_MAX_KPALIVE_PKT 3
#define RTW_WOWLAN_MAX_KPALIVE_PKT_SZ 512
struct rtw_wowlan_keepalive_packet{
u8 packet_id;
int payload_len;
u8 *payload;
u32 data_interval;
_wowTimer keepalive_tmr;
};
struct rtw_wowlan_ops {
int (*DevWowlanInit)(void);
int (*DevWowlanEnable)(void);
int (*DevWowlanDisable)(void);
int (*DevWowlanWakeUp)(void);
int (*DevWowlanSleep)(void);
};
/**
* enum rtw_wowlan_proto_offloads - enabled protocol offloads
* @RTW_WOWLAN_PROTO_OFFLOAD_ARP: ARP data is enabled
*/
enum rtw_wowlan_proto_offloads {
RTW_WOWLAN_PROTO_OFFLOAD_ARP = BIT(0),
RTW_WOWLAN_PROTO_OFFLOAD_MAX = 0x7FFFFFFF
};
/**
* struct rtw_wowlan_proto_offload_common - ARP/NS offload common part
* @enabled: enable flags
* @remote_ipv4_addr: remote address to answer to (or zero if all)
* @host_ipv4_addr: our IPv4 address to respond to queries for
* @arp_mac_addr: our MAC address for ARP responses
* @reserved: unused
*/
struct rtw_wowlan_proto_offload_common{
int proto_enabled;
u32 remote_ipv4_addr;
u32 host_ipv4_addr;
u8 host_mac_addr[ETH_ALEN];
u16 reserved;
};
struct rtw_wowlan {
_wowlock wow_mutex;
bool enabled;
struct rtw_wowlan_status status;
struct rtw_wowlan_ops ops;
struct rtw_wowlan_proto_offload_common proto;
bool proto_offload_enabled;
struct rtw_wowlan_rx_filter *rx_filter[RTW_WOWLAN_MAX_RX_FILTERS];
bool rx_filter_enabled[RTW_WOWLAN_MAX_RX_FILTERS];/* RX Data filter rule state - enabled/disabled */
struct rtw_wowlan_keepalive_packet *tx_keepalive[RTW_WOWLAN_MAX_KPALIVE_PKT];
bool tx_keepalive_enabled[RTW_WOWLAN_MAX_KPALIVE_PKT];/* TX keep avlive rule state - enabled/disabled */
};
#define eqMacAddr(a,b) ( ((a)[0]==(b)[0] && (a)[1]==(b)[1] && (a)[2]==(b)[2] && (a)[3]==(b)[3] && (a)[4]==(b)[4] && (a)[5]==(b)[5]) ? 1:0 )
#define cpMacAddr(des,src) ((des)[0]=(src)[0],(des)[1]=(src)[1],(des)[2]=(src)[2],(des)[3]=(src)[3],(des)[4]=(src)[4],(des)[5]=(src)[5])
#define cpIpAddr(des,src) ((des)[0]=(src)[0],(des)[1]=(src)[1],(des)[2]=(src)[2],(des)[3]=(src)[3])
#define RTW_WOWLAN_GET_ARP_PKT_OPERATION(__pHeader) ReadEF2Byte( ((u8*)(__pHeader)) + 6)
#define RTW_WOWLAN_GET_ARP_PKT_SENDER_MAC_ADDR(__pHeader, _val) cpMacAddr((u8*)(_val), ((u8*)(__pHeader))+8)
#define RTW_WOWLAN_GET_ARP_PKT_SENDER_IP_ADDR(__pHeader, _val) cpIpAddr((u8*)(_val), ((u8*)(__pHeader))+14)
#define RTW_WOWLAN_GET_ARP_PKT_TARGET_MAC_ADDR(__pHeader, _val) cpMacAddr((u8*)(_val), ((u8*)(__pHeader))+18)
#define RTW_WOWLAN_GET_ARP_PKT_TARGET_IP_ADDR(__pHeader, _val) cpIpAddr((u8*)(_val), ((u8*)(__pHeader))+24)
#define RTW_WOWLAN_SET_ARP_PKT_HW(__pHeader, __Value) WriteEF2Byte( ((u8*)(__pHeader)) + 0, __Value)
#define RTW_WOWLAN_SET_ARP_PKT_PROTOCOL(__pHeader, __Value) WriteEF2Byte( ((u8*)(__pHeader)) + 2, __Value)
#define RTW_WOWLAN_SET_ARP_PKT_HW_ADDR_LEN(__pHeader, __Value) WriteEF1Byte( ((u8*)(__pHeader)) + 4, __Value)
#define RTW_WOWLAN_SET_ARP_PKT_PROTOCOL_ADDR_LEN(__pHeader, __Value) WriteEF1Byte( ((u8*)(__pHeader)) + 5, __Value)
#define RTW_WOWLAN_SET_ARP_PKT_OPERATION(__pHeader, __Value) WriteEF2Byte( ((u8*)(__pHeader)) + 6, __Value)
#define RTW_WOWLAN_SET_ARP_PKT_SENDER_MAC_ADDR(__pHeader, _val) cpMacAddr(((u8*)(__pHeader))+8, (u8*)(_val))
#define RTW_WOWLAN_SET_ARP_PKT_SENDER_IP_ADDR(__pHeader, _val) cpIpAddr(((u8*)(__pHeader))+14, (u8*)(_val))
#define RTW_WOWLAN_SET_ARP_PKT_TARGET_MAC_ADDR(__pHeader, _val) cpMacAddr(((u8*)(__pHeader))+18, (u8*)(_val))
#define RTW_WOWLAN_SET_ARP_PKT_TARGET_IP_ADDR(__pHeader, _val) cpIpAddr(((u8*)(__pHeader))+24, (u8*)(_val))
#define RTW_WOWLAN_ARP_PKT_LEN 0x2A
#define RTW_WOWLAN_ARP_PKT_OPERATION_REQ 0x0100 //arp request
#define RTW_WOWLAN_ARP_PKT_OPERATION_RSP 0x0200 //arp response
extern u8 key_2char2num(u8 hch, u8 lch);
extern _LONG_CALL_ void __rtl_memDump_v1_00(const u8 *start, u32 size, char * strHeader);
#define rtw_wowlan_DumpForBytes(pData, Len) __rtl_memDump_v1_00(pData, Len, NULL)
#define PWOWLAN_TO_STATUS(pwowlan) (&pwowlan->status)
#define PWOWLAN_TO_OPS(pwowlan) (&pwowlan->ops)
#define PWOWLAN_TO_PROTO(pwowlan) (&pwowlan->proto)
#define PWOWLAN_TO_RX_FILTER(pwowlan) (pwowlan->rx_filter)
#define PWOWLAN_TO_TX_KEEPALIVE(pwowlan) (pwowlan->tx_keepalive)
/**
* rtw_wowlan_init: initialize wowlan service
* arg: None
* return: _SUCCESS or _FAIL
*/
extern int rtw_wowlan_init(void);
/**
* cmd_wowlan_service: input commands to configure wowlan service
* arg:
* @argc: number of input parameter
* @argv: content of input string
* return: None
*/
extern void cmd_wowlan_service(int argc, char **argv);
/**
* rtw_wowlan_process_rx_packet: entry for packet process in wowlan service once it starts
* arg:
* @rx_pkt: receive packet from wlan/ethernet
* @pkt_len: receive packet length
* return: _SUCCESS or _FAIL
*/
extern int rtw_wowlan_process_rx_packet(char *rx_pkt, u16 pkt_len);
/**
* rtw_wowlan_wakeup_process: wake up process once the reasons are matched,
* refer to enum rtw_wowlan_wakeup_reason
* arg:
* @reason: wake up reason, refer to enum rtw_wowlan_wakeup_reason
* return: None
*/
extern void rtw_wowlan_wakeup_process(int reason);
/**
* rtw_wowlan_is_enabled: if wowlan service is already enabled
* this function is called in rx path and wifi_inidication when wowlan service is running
* arg: None
* return: _True if enable or _False if disable
*/
extern int rtw_wowlan_is_enabled(void);
/**
* rtw_wowlan_get_wk_reason: query wake up reason, refer to enum rtw_wowlan_wakeup_reason
* arg: None
* return: wakeup_reason
*/
extern int rtw_wowlan_get_wk_reason(void);
/**
* rtw_wowlan_dev_sleep: sleep process on Ameba side, pull control for example
* this function is linked to dev_wowlan_sleep_process() in dev_wowlan.c
* arg: None
* return: None
*/
extern void rtw_wowlan_dev_sleep(void);
#endif

View File

@@ -0,0 +1,589 @@
/*
* SSL/TLS interface definition
* Copyright (c) 2004-2013, Jouni Malinen <j@w1.fi>
*
* This software may be distributed under the terms of the BSD license.
* See README for more details.
*/
#ifndef TLS_H
#define TLS_H
struct tls_connection;
struct tls_random {
const u8 *client_random;
size_t client_random_len;
const u8 *server_random;
size_t server_random_len;
};
enum tls_event {
TLS_CERT_CHAIN_SUCCESS,
TLS_CERT_CHAIN_FAILURE,
TLS_PEER_CERTIFICATE,
TLS_ALERT
};
/*
* Note: These are used as identifier with external programs and as such, the
* values must not be changed.
*/
enum tls_fail_reason {
TLS_FAIL_UNSPECIFIED = 0,
TLS_FAIL_UNTRUSTED = 1,
TLS_FAIL_REVOKED = 2,
TLS_FAIL_NOT_YET_VALID = 3,
TLS_FAIL_EXPIRED = 4,
TLS_FAIL_SUBJECT_MISMATCH = 5,
TLS_FAIL_ALTSUBJECT_MISMATCH = 6,
TLS_FAIL_BAD_CERTIFICATE = 7,
TLS_FAIL_SERVER_CHAIN_PROBE = 8,
TLS_FAIL_DOMAIN_SUFFIX_MISMATCH = 9,
TLS_FAIL_DOMAIN_MISMATCH = 10,
};
#define TLS_MAX_ALT_SUBJECT 10
union tls_event_data {
struct {
int depth;
const char *subject;
enum tls_fail_reason reason;
const char *reason_txt;
const struct wpabuf *cert;
} cert_fail;
struct {
int depth;
const char *subject;
const struct wpabuf *cert;
const u8 *hash;
size_t hash_len;
const char *altsubject[TLS_MAX_ALT_SUBJECT];
int num_altsubject;
} peer_cert;
struct {
int is_local;
const char *type;
const char *description;
} alert;
};
struct tls_config {
const char *opensc_engine_path;
const char *pkcs11_engine_path;
const char *pkcs11_module_path;
int fips_mode;
int cert_in_cb;
const char *openssl_ciphers;
unsigned int tls_session_lifetime;
void (*event_cb)(void *ctx, enum tls_event ev,
union tls_event_data *data);
void *cb_ctx;
};
#define TLS_CONN_ALLOW_SIGN_RSA_MD5 BIT(0)
#define TLS_CONN_DISABLE_TIME_CHECKS BIT(1)
#define TLS_CONN_DISABLE_SESSION_TICKET BIT(2)
#define TLS_CONN_REQUEST_OCSP BIT(3)
#define TLS_CONN_REQUIRE_OCSP BIT(4)
#define TLS_CONN_DISABLE_TLSv1_1 BIT(5)
#define TLS_CONN_DISABLE_TLSv1_2 BIT(6)
#define TLS_CONN_EAP_FAST BIT(7)
#define TLS_CONN_DISABLE_TLSv1_0 BIT(8)
/**
* struct tls_connection_params - Parameters for TLS connection
* @ca_cert: File or reference name for CA X.509 certificate in PEM or DER
* format
* @ca_cert_blob: ca_cert as inlined data or %NULL if not used
* @ca_cert_blob_len: ca_cert_blob length
* @ca_path: Path to CA certificates (OpenSSL specific)
* @subject_match: String to match in the subject of the peer certificate or
* %NULL to allow all subjects
* @altsubject_match: String to match in the alternative subject of the peer
* certificate or %NULL to allow all alternative subjects
* @suffix_match: String to suffix match in the dNSName or CN of the peer
* certificate or %NULL to allow all domain names. This may allow subdomains an
* wildcard certificates. Each domain name label must have a full match.
* @domain_match: String to match in the dNSName or CN of the peer
* certificate or %NULL to allow all domain names. This requires a full,
* case-insensitive match.
* @client_cert: File or reference name for client X.509 certificate in PEM or
* DER format
* @client_cert_blob: client_cert as inlined data or %NULL if not used
* @client_cert_blob_len: client_cert_blob length
* @private_key: File or reference name for client private key in PEM or DER
* format (traditional format (RSA PRIVATE KEY) or PKCS#8 (PRIVATE KEY)
* @private_key_blob: private_key as inlined data or %NULL if not used
* @private_key_blob_len: private_key_blob length
* @private_key_passwd: Passphrase for decrypted private key, %NULL if no
* passphrase is used.
* @dh_file: File name for DH/DSA data in PEM format, or %NULL if not used
* @dh_blob: dh_file as inlined data or %NULL if not used
* @dh_blob_len: dh_blob length
* @engine: 1 = use engine (e.g., a smartcard) for private key operations
* (this is OpenSSL specific for now)
* @engine_id: engine id string (this is OpenSSL specific for now)
* @ppin: pointer to the pin variable in the configuration
* (this is OpenSSL specific for now)
* @key_id: the private key's id when using engine (this is OpenSSL
* specific for now)
* @cert_id: the certificate's id when using engine
* @ca_cert_id: the CA certificate's id when using engine
* @openssl_ciphers: OpenSSL cipher configuration
* @flags: Parameter options (TLS_CONN_*)
* @ocsp_stapling_response: DER encoded file with cached OCSP stapling response
* or %NULL if OCSP is not enabled
*
* TLS connection parameters to be configured with tls_connection_set_params()
* and tls_global_set_params().
*
* Certificates and private key can be configured either as a reference name
* (file path or reference to certificate store) or by providing the same data
* as a pointer to the data in memory. Only one option will be used for each
* field.
*/
struct tls_connection_params {
const char *ca_cert;
const u8 *ca_cert_blob;
size_t ca_cert_blob_len;
const char *ca_path;
const char *subject_match;
const char *altsubject_match;
const char *suffix_match;
const char *domain_match;
const char *client_cert;
const u8 *client_cert_blob;
size_t client_cert_blob_len;
const char *private_key;
const u8 *private_key_blob;
size_t private_key_blob_len;
const char *private_key_passwd;
const char *dh_file;
const u8 *dh_blob;
size_t dh_blob_len;
/* OpenSSL specific variables */
int engine;
const char *engine_id;
const char *pin;
const char *key_id;
const char *cert_id;
const char *ca_cert_id;
const char *openssl_ciphers;
unsigned int flags;
const char *ocsp_stapling_response;
};
/**
* tls_init - Initialize TLS library
* @conf: Configuration data for TLS library
* Returns: Context data to be used as tls_ctx in calls to other functions,
* or %NULL on failure.
*
* Called once during program startup and once for each RSN pre-authentication
* session. In other words, there can be two concurrent TLS contexts. If global
* library initialization is needed (i.e., one that is shared between both
* authentication types), the TLS library wrapper should maintain a reference
* counter and do global initialization only when moving from 0 to 1 reference.
*/
//ssl_context * tls_init(const struct tls_config *conf);
void * tls_init(const struct tls_config *conf);
/**
* tls_deinit - Deinitialize TLS library
* @tls_ctx: TLS context data from tls_init()
*
* Called once during program shutdown and once for each RSN pre-authentication
* session. If global library deinitialization is needed (i.e., one that is
* shared between both authentication types), the TLS library wrapper should
* maintain a reference counter and do global deinitialization only when moving
* from 1 to 0 references.
*/
void tls_deinit(void *tls_ctx);
/**
* tls_get_errors - Process pending errors
* @tls_ctx: TLS context data from tls_init()
* Returns: Number of found error, 0 if no errors detected.
*
* Process all pending TLS errors.
*/
int tls_get_errors(void *tls_ctx);
/**
* tls_connection_init - Initialize a new TLS connection
* @tls_ctx: TLS context data from tls_init()
* Returns: Connection context data, conn for other function calls
*/
struct tls_connection * tls_connection_init(void *tls_ctx);
/**
* tls_connection_deinit - Free TLS connection data
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
*
* Release all resources allocated for TLS connection.
*/
void tls_connection_deinit(void *tls_ctx, struct tls_connection *conn);
/**
* tls_connection_established - Has the TLS connection been completed?
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* Returns: 1 if TLS connection has been completed, 0 if not.
*/
int tls_connection_established(void *tls_ctx, struct tls_connection *conn);
/**
* tls_connection_shutdown - Shutdown TLS connection
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* Returns: 0 on success, -1 on failure
*
* Shutdown current TLS connection without releasing all resources. New
* connection can be started by using the same conn without having to call
* tls_connection_init() or setting certificates etc. again. The new
* connection should try to use session resumption.
*/
int tls_connection_shutdown(void *tls_ctx, struct tls_connection *conn);
enum {
TLS_SET_PARAMS_ENGINE_PRV_BAD_PIN = -4,
TLS_SET_PARAMS_ENGINE_PRV_VERIFY_FAILED = -3,
TLS_SET_PARAMS_ENGINE_PRV_INIT_FAILED = -2
};
/**
* tls_connection_set_params - Set TLS connection parameters
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* @params: Connection parameters
* Returns: 0 on success, -1 on failure,
* TLS_SET_PARAMS_ENGINE_PRV_INIT_FAILED (-2) on error causing PKCS#11 engine
* failure, or
* TLS_SET_PARAMS_ENGINE_PRV_VERIFY_FAILED (-3) on failure to verify the
* PKCS#11 engine private key, or
* TLS_SET_PARAMS_ENGINE_PRV_BAD_PIN (-4) on PIN error causing PKCS#11 engine
* failure.
*/
int __must_check
tls_connection_set_params(void *tls_ctx, struct tls_connection *conn,
const struct tls_connection_params *params);
/**
* tls_global_set_params - Set TLS parameters for all TLS connection
* @tls_ctx: TLS context data from tls_init()
* @params: Global TLS parameters
* Returns: 0 on success, -1 on failure,
* TLS_SET_PARAMS_ENGINE_PRV_INIT_FAILED (-2) on error causing PKCS#11 engine
* failure, or
* TLS_SET_PARAMS_ENGINE_PRV_VERIFY_FAILED (-3) on failure to verify the
* PKCS#11 engine private key, or
* TLS_SET_PARAMS_ENGINE_PRV_BAD_PIN (-4) on PIN error causing PKCS#11 engine
* failure.
*/
int __must_check tls_global_set_params(
void *tls_ctx, const struct tls_connection_params *params);
/**
* tls_global_set_verify - Set global certificate verification options
* @tls_ctx: TLS context data from tls_init()
* @check_crl: 0 = do not verify CRLs, 1 = verify CRL for the user certificate,
* 2 = verify CRL for all certificates
* Returns: 0 on success, -1 on failure
*/
int __must_check tls_global_set_verify(void *tls_ctx, int check_crl);
/**
* tls_connection_set_verify - Set certificate verification options
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* @verify_peer: 1 = verify peer certificate
* @flags: Connection flags (TLS_CONN_*)
* @session_ctx: Session caching context or %NULL to use default
* @session_ctx_len: Length of @session_ctx in bytes.
* Returns: 0 on success, -1 on failure
*/
int __must_check tls_connection_set_verify(void *tls_ctx,
struct tls_connection *conn,
int verify_peer,
unsigned int flags,
const u8 *session_ctx,
size_t session_ctx_len);
/**
* tls_connection_get_random - Get random data from TLS connection
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* @data: Structure of client/server random data (filled on success)
* Returns: 0 on success, -1 on failure
*/
int __must_check tls_connection_get_random(void *tls_ctx,
struct tls_connection *conn,
struct tls_random *data);
/**
* tls_connection_prf - Use TLS-PRF to derive keying material
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* @label: Label (e.g., description of the key) for PRF
* @server_random_first: seed is 0 = client_random|server_random,
* 1 = server_random|client_random
* @skip_keyblock: Skip TLS key block from the beginning of PRF output
* @out: Buffer for output data from TLS-PRF
* @out_len: Length of the output buffer
* Returns: 0 on success, -1 on failure
*
* tls_connection_prf() is required so that further keying material can be
* derived from the master secret. Example implementation of this function is in
* tls_prf_sha1_md5() when it is called with seed set to
* client_random|server_random (or server_random|client_random). For TLSv1.2 and
* newer, a different PRF is needed, though.
*/
int __must_check tls_connection_prf(void *tls_ctx,
struct tls_connection *conn,
const char *label,
int server_random_first,
int skip_keyblock,
u8 *out, size_t out_len);
/**
* tls_connection_handshake - Process TLS handshake (client side)
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* @in_data: Input data from TLS server
* @appl_data: Pointer to application data pointer, or %NULL if dropped
* Returns: Output data, %NULL on failure
*
* The caller is responsible for freeing the returned output data. If the final
* handshake message includes application data, this is decrypted and
* appl_data (if not %NULL) is set to point this data. The caller is
* responsible for freeing appl_data.
*
* This function is used during TLS handshake. The first call is done with
* in_data == %NULL and the library is expected to return ClientHello packet.
* This packet is then send to the server and a response from server is given
* to TLS library by calling this function again with in_data pointing to the
* TLS message from the server.
*
* If the TLS handshake fails, this function may return %NULL. However, if the
* TLS library has a TLS alert to send out, that should be returned as the
* output data. In this case, tls_connection_get_failed() must return failure
* (> 0).
*
* tls_connection_established() should return 1 once the TLS handshake has been
* completed successfully.
*/
struct wpabuf * tls_connection_handshake(void *tls_ctx,
struct tls_connection *conn,
const struct wpabuf *in_data,
struct wpabuf **appl_data);
struct wpabuf * tls_connection_handshake2(void *tls_ctx,
struct tls_connection *conn,
const struct wpabuf *in_data,
struct wpabuf **appl_data,
int *more_data_needed);
/**
* tls_connection_server_handshake - Process TLS handshake (server side)
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* @in_data: Input data from TLS peer
* @appl_data: Pointer to application data pointer, or %NULL if dropped
* Returns: Output data, %NULL on failure
*
* The caller is responsible for freeing the returned output data.
*/
struct wpabuf * tls_connection_server_handshake(void *tls_ctx,
struct tls_connection *conn,
const struct wpabuf *in_data,
struct wpabuf **appl_data);
/**
* tls_connection_encrypt - Encrypt data into TLS tunnel
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* @in_data: Plaintext data to be encrypted
* Returns: Encrypted TLS data or %NULL on failure
*
* This function is used after TLS handshake has been completed successfully to
* send data in the encrypted tunnel. The caller is responsible for freeing the
* returned output data.
*/
struct wpabuf * tls_connection_encrypt(void *tls_ctx,
struct tls_connection *conn,
const struct wpabuf *in_data);
/**
* tls_connection_decrypt - Decrypt data from TLS tunnel
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* @in_data: Encrypted TLS data
* Returns: Decrypted TLS data or %NULL on failure
*
* This function is used after TLS handshake has been completed successfully to
* receive data from the encrypted tunnel. The caller is responsible for
* freeing the returned output data.
*/
struct wpabuf * tls_connection_decrypt(void *tls_ctx,
struct tls_connection *conn,
const struct wpabuf *in_data);
struct wpabuf * tls_connection_decrypt2(void *tls_ctx,
struct tls_connection *conn,
const struct wpabuf *in_data,
int *more_data_needed);
/**
* tls_connection_resumed - Was session resumption used
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* Returns: 1 if current session used session resumption, 0 if not
*/
int tls_connection_resumed(void *tls_ctx, struct tls_connection *conn);
enum {
TLS_CIPHER_NONE,
TLS_CIPHER_RC4_SHA /* 0x0005 */,
TLS_CIPHER_AES128_SHA /* 0x002f */,
TLS_CIPHER_RSA_DHE_AES128_SHA /* 0x0031 */,
TLS_CIPHER_ANON_DH_AES128_SHA /* 0x0034 */
};
/**
* tls_connection_set_cipher_list - Configure acceptable cipher suites
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* @ciphers: Zero (TLS_CIPHER_NONE) terminated list of allowed ciphers
* (TLS_CIPHER_*).
* Returns: 0 on success, -1 on failure
*/
int __must_check tls_connection_set_cipher_list(void *tls_ctx,
struct tls_connection *conn,
u8 *ciphers);
/**
* tls_get_version - Get the current TLS version number
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* @buf: Buffer for returning the TLS version number
* @buflen: buf size
* Returns: 0 on success, -1 on failure
*
* Get the currently used TLS version number.
*/
int __must_check tls_get_version(void *tls_ctx, struct tls_connection *conn,
char *buf, size_t buflen);
/**
* tls_get_cipher - Get current cipher name
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* @buf: Buffer for the cipher name
* @buflen: buf size
* Returns: 0 on success, -1 on failure
*
* Get the name of the currently used cipher.
*/
int __must_check tls_get_cipher(void *tls_ctx, struct tls_connection *conn,
char *buf, size_t buflen);
/**
* tls_connection_enable_workaround - Enable TLS workaround options
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* Returns: 0 on success, -1 on failure
*
* This function is used to enable connection-specific workaround options for
* buffer SSL/TLS implementations.
*/
int __must_check tls_connection_enable_workaround(void *tls_ctx,
struct tls_connection *conn);
/**
* tls_connection_client_hello_ext - Set TLS extension for ClientHello
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* @ext_type: Extension type
* @data: Extension payload (%NULL to remove extension)
* @data_len: Extension payload length
* Returns: 0 on success, -1 on failure
*/
int __must_check tls_connection_client_hello_ext(void *tls_ctx,
struct tls_connection *conn,
int ext_type, const u8 *data,
size_t data_len);
/**
* tls_connection_get_failed - Get connection failure status
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
*
* Returns >0 if connection has failed, 0 if not.
*/
int tls_connection_get_failed(void *tls_ctx, struct tls_connection *conn);
/**
* tls_connection_get_read_alerts - Get connection read alert status
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* Returns: Number of times a fatal read (remote end reported error) has
* happened during this connection.
*/
int tls_connection_get_read_alerts(void *tls_ctx, struct tls_connection *conn);
/**
* tls_connection_get_write_alerts - Get connection write alert status
* @tls_ctx: TLS context data from tls_init()
* @conn: Connection context data from tls_connection_init()
* Returns: Number of times a fatal write (locally detected error) has happened
* during this connection.
*/
int tls_connection_get_write_alerts(void *tls_ctx,
struct tls_connection *conn);
typedef int (*tls_session_ticket_cb)
(void *ctx, const u8 *ticket, size_t len, const u8 *client_random,
const u8 *server_random, u8 *master_secret);
int __must_check tls_connection_set_session_ticket_cb(
void *tls_ctx, struct tls_connection *conn,
tls_session_ticket_cb cb, void *ctx);
void tls_connection_set_log_cb(struct tls_connection *conn,
void (*log_cb)(void *ctx, const char *msg),
void *ctx);
#define TLS_BREAK_VERIFY_DATA BIT(0)
#define TLS_BREAK_SRV_KEY_X_HASH BIT(1)
#define TLS_BREAK_SRV_KEY_X_SIGNATURE BIT(2)
#define TLS_DHE_PRIME_511B BIT(3)
#define TLS_DHE_PRIME_767B BIT(4)
#define TLS_DHE_PRIME_15 BIT(5)
#define TLS_DHE_PRIME_58B BIT(6)
#define TLS_DHE_NON_PRIME BIT(7)
void tls_connection_set_test_flags(struct tls_connection *conn, u32 flags);
int tls_get_library_version(char *buf, size_t buf_len);
void tls_connection_set_success_data(struct tls_connection *conn,
struct wpabuf *data);
void tls_connection_set_success_data_resumed(struct tls_connection *conn);
const struct wpabuf *
tls_connection_get_success_data(struct tls_connection *conn);
void tls_connection_remove_session(struct tls_connection *conn);
#endif /* TLS_H */

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,548 @@
/*
* wpa_supplicant/hostapd / common helper functions, etc.
* Copyright (c) 2002-2007, Jouni Malinen <j@w1.fi>
*
* This software may be distributed under the terms of the BSD license.
* See README for more details.
*/
#ifndef COMMON_H
#define COMMON_H
#include "utils/os.h"
#define TO_TEST_WPS 0
#define ETH_ALEN 6
#if defined(__linux__) || defined(__GLIBC__)
#include <endian.h>
#include <byteswap.h>
#endif /* __linux__ */
#if defined(PLATFORM_FREERTOS)
//#include "little_endian.h"
//#include "basic_types.h"
#endif /* PLATFORM_FREERTOS */
#if defined(__FreeBSD__) || defined(__NetBSD__) || defined(__DragonFly__) || \
defined(__OpenBSD__)
#include <sys/types.h>
#include <sys/endian.h>
#define __BYTE_ORDER _BYTE_ORDER
#define __LITTLE_ENDIAN _LITTLE_ENDIAN
#define __BIG_ENDIAN _BIG_ENDIAN
#ifdef __OpenBSD__
#define bswap_16 swap16
#define bswap_32 swap32
#define bswap_64 swap64
#else /* __OpenBSD__ */
#define bswap_16 bswap16
#define bswap_32 bswap32
#define bswap_64 bswap64
#endif /* __OpenBSD__ */
#endif /* defined(__FreeBSD__) || defined(__NetBSD__) || * defined(__DragonFly__) || defined(__OpenBSD__) */
#ifdef __APPLE__
#include <sys/types.h>
#include <machine/endian.h>
#define __BYTE_ORDER _BYTE_ORDER
#define __LITTLE_ENDIAN _LITTLE_ENDIAN
#define __BIG_ENDIAN _BIG_ENDIAN
static inline unsigned short bswap_16(unsigned short v)
{
return ((v & 0xff) << 8) | (v >> 8);
}
static inline unsigned int bswap_32(unsigned int v)
{
return ((v & 0xff) << 24) | ((v & 0xff00) << 8) |
((v & 0xff0000) >> 8) | (v >> 24);
}
#endif /* __APPLE__ */
#ifdef CONFIG_TI_COMPILER
#define __BIG_ENDIAN 4321
#define __LITTLE_ENDIAN 1234
#ifdef __big_endian__
#define __BYTE_ORDER __BIG_ENDIAN
#else
#define __BYTE_ORDER __LITTLE_ENDIAN
#endif
#endif /* CONFIG_TI_COMPILER */
#ifdef CONFIG_NATIVE_WINDOWS
#include <winsock.h>
typedef int socklen_t;
#ifndef MSG_DONTWAIT
#define MSG_DONTWAIT 0 /* not supported */
#endif
#endif /* CONFIG_NATIVE_WINDOWS */
#ifdef _MSC_VER
#define inline __inline
#undef vsnprintf
#define vsnprintf _vsnprintf
#undef close
#define close closesocket
#endif /* _MSC_VER */
/* Define platform specific integer types */
#ifdef _MSC_VER
typedef UINT64 u64;
typedef UINT32 u32;
typedef UINT16 u16;
typedef UINT8 u8;
typedef INT64 s64;
typedef INT32 s32;
typedef INT16 s16;
typedef INT8 s8;
#define WPA_TYPES_DEFINED
#endif /* _MSC_VER */
#ifdef __vxworks
typedef unsigned long long u64;
typedef UINT32 u32;
typedef UINT16 u16;
typedef UINT8 u8;
typedef long long s64;
typedef INT32 s32;
typedef INT16 s16;
typedef INT8 s8;
#define WPA_TYPES_DEFINED
#endif /* __vxworks */
#ifdef CONFIG_TI_COMPILER
#ifdef _LLONG_AVAILABLE
typedef unsigned long long u64;
#else
/*
* TODO: 64-bit variable not available. Using long as a workaround to test the
* build, but this will likely not work for all operations.
*/
typedef unsigned long u64;
#endif
typedef unsigned int u32;
typedef unsigned short u16;
typedef unsigned char u8;
#define WPA_TYPES_DEFINED
#endif /* CONFIG_TI_COMPILER */
#ifndef WPA_TYPES_DEFINED
#ifdef CONFIG_USE_INTTYPES_H
#include <inttypes.h>
#else
//#include <stdint.h>
#endif
#if 0
typedef uint64_t u64;
typedef uint32_t u32;
typedef uint16_t u16;
typedef uint8_t u8;
typedef int64_t s64;
typedef int32_t s32;
typedef int16_t s16;
typedef int8_t s8;
#endif
#define WPA_TYPES_DEFINED
#endif /* !WPA_TYPES_DEFINED */
/* Define platform specific byte swapping macros */
#if defined(__CYGWIN__) || defined(CONFIG_NATIVE_WINDOWS)
static inline unsigned short wpa_swap_16(unsigned short v)
{
return ((v & 0xff) << 8) | (v >> 8);
}
static inline unsigned int wpa_swap_32(unsigned int v)
{
return ((v & 0xff) << 24) | ((v & 0xff00) << 8) |
((v & 0xff0000) >> 8) | (v >> 24);
}
#define le_to_host16(n) (n)
#define host_to_le16(n) (n)
#define be_to_host16(n) wpa_swap_16(n)
#define host_to_be16(n) wpa_swap_16(n)
#define le_to_host32(n) (n)
#define be_to_host32(n) wpa_swap_32(n)
#define host_to_be32(n) wpa_swap_32(n)
#define WPA_BYTE_SWAP_DEFINED
#endif /* __CYGWIN__ || CONFIG_NATIVE_WINDOWS */
#ifndef WPA_BYTE_SWAP_DEFINED
#if 0
#ifndef __BYTE_ORDER
#ifndef __LITTLE_ENDIAN
#ifndef __BIG_ENDIAN
#define __LITTLE_ENDIAN 1234
#define __BIG_ENDIAN 4321
#if defined(sparc)
#define __BYTE_ORDER __BIG_ENDIAN
#endif
#endif /* __BIG_ENDIAN */
#endif /* __LITTLE_ENDIAN */
#endif /* __BYTE_ORDER */
#else
#ifndef __LITTLE_ENDIAN
#define __LITTLE_ENDIAN 1234
#endif
#ifndef __BIG_ENDIAN
#define __BIG_ENDIAN 4321
#endif
#ifndef __BYTE_ORDER
#define __BYTE_ORDER __LITTLE_ENDIAN
#endif
#endif
#if __BYTE_ORDER == __LITTLE_ENDIAN
#define le_to_host16(n) ((__force u16) (le16) (n))
#define host_to_le16(n) ((__force le16) (u16) (n))
#define be_to_host16(n) bswap_16((__force u16) (be16) (n))
#define host_to_be16(n) ((__force be16) bswap_16((n)))
#define le_to_host32(n) ((__force u32) (le32) (n))
#define host_to_le32(n) ((__force le32) (u32) (n))
#define be_to_host32(n) bswap_32((__force u32) (be32) (n))
#define host_to_be32(n) ((__force be32) bswap_32((n)))
#define le_to_host64(n) ((__force u64) (le64) (n))
#define host_to_le64(n) ((__force le64) (u64) (n))
#define be_to_host64(n) bswap_64((__force u64) (be64) (n))
#define host_to_be64(n) ((__force be64) bswap_64((n)))
#elif __BYTE_ORDER == __BIG_ENDIAN
#define le_to_host16(n) bswap_16(n)
#define host_to_le16(n) bswap_16(n)
#define be_to_host16(n) (n)
#define host_to_be16(n) (n)
#define le_to_host32(n) bswap_32(n)
#define be_to_host32(n) (n)
#define host_to_be32(n) (n)
#define le_to_host64(n) bswap_64(n)
#define host_to_le64(n) bswap_64(n)
#define be_to_host64(n) (n)
#define host_to_be64(n) (n)
#ifndef WORDS_BIGENDIAN
#define WORDS_BIGENDIAN
#endif
#else
//#error Could not determine CPU byte order
#endif
#define WPA_BYTE_SWAP_DEFINED
#endif /* !WPA_BYTE_SWAP_DEFINED */
/* Macros for handling unaligned memory accesses */
#define WPA_GET_BE16(a) ((u16) (((a)[0] << 8) | (a)[1]))
#define WPA_PUT_BE16(a, val) \
do { \
(a)[0] = ((u16) (val)) >> 8; \
(a)[1] = ((u16) (val)) & 0xff; \
} while (0)
#define WPA_GET_LE16(a) ((u16) (((a)[1] << 8) | (a)[0]))
#define WPA_PUT_LE16(a, val) \
do { \
(a)[1] = ((u16) (val)) >> 8; \
(a)[0] = ((u16) (val)) & 0xff; \
} while (0)
#define WPA_GET_BE24(a) ((((u32) (a)[0]) << 16) | (((u32) (a)[1]) << 8) | \
((u32) (a)[2]))
#define WPA_PUT_BE24(a, val) \
do { \
(a)[0] = (u8) ((((u32) (val)) >> 16) & 0xff); \
(a)[1] = (u8) ((((u32) (val)) >> 8) & 0xff); \
(a)[2] = (u8) (((u32) (val)) & 0xff); \
} while (0)
#define WPA_GET_BE32(a) ((((u32) (a)[0]) << 24) | (((u32) (a)[1]) << 16) | \
(((u32) (a)[2]) << 8) | ((u32) (a)[3]))
#define WPA_PUT_BE32(a, val) \
do { \
(a)[0] = (u8) ((((u32) (val)) >> 24) & 0xff); \
(a)[1] = (u8) ((((u32) (val)) >> 16) & 0xff); \
(a)[2] = (u8) ((((u32) (val)) >> 8) & 0xff); \
(a)[3] = (u8) (((u32) (val)) & 0xff); \
} while (0)
#define WPA_GET_LE32(a) ((((u32) (a)[3]) << 24) | (((u32) (a)[2]) << 16) | \
(((u32) (a)[1]) << 8) | ((u32) (a)[0]))
#define WPA_PUT_LE32(a, val) \
do { \
(a)[3] = (u8) ((((u32) (val)) >> 24) & 0xff); \
(a)[2] = (u8) ((((u32) (val)) >> 16) & 0xff); \
(a)[1] = (u8) ((((u32) (val)) >> 8) & 0xff); \
(a)[0] = (u8) (((u32) (val)) & 0xff); \
} while (0)
#define WPA_GET_BE64(a) ((((u64) (a)[0]) << 56) | (((u64) (a)[1]) << 48) | \
(((u64) (a)[2]) << 40) | (((u64) (a)[3]) << 32) | \
(((u64) (a)[4]) << 24) | (((u64) (a)[5]) << 16) | \
(((u64) (a)[6]) << 8) | ((u64) (a)[7]))
#define WPA_PUT_BE64(a, val) \
do { \
(a)[0] = (u8) (((u64) (val)) >> 56); \
(a)[1] = (u8) (((u64) (val)) >> 48); \
(a)[2] = (u8) (((u64) (val)) >> 40); \
(a)[3] = (u8) (((u64) (val)) >> 32); \
(a)[4] = (u8) (((u64) (val)) >> 24); \
(a)[5] = (u8) (((u64) (val)) >> 16); \
(a)[6] = (u8) (((u64) (val)) >> 8); \
(a)[7] = (u8) (((u64) (val)) & 0xff); \
} while (0)
#define WPA_GET_LE64(a) ((((u64) (a)[7]) << 56) | (((u64) (a)[6]) << 48) | \
(((u64) (a)[5]) << 40) | (((u64) (a)[4]) << 32) | \
(((u64) (a)[3]) << 24) | (((u64) (a)[2]) << 16) | \
(((u64) (a)[1]) << 8) | ((u64) (a)[0]))
#ifndef ETH_ALEN
#define ETH_ALEN 6
#endif
#ifndef IFNAMSIZ
#define IFNAMSIZ 16
#endif
#ifndef ETH_P_ALL
#define ETH_P_ALL 0x0003
#endif
#ifndef ETH_P_80211_ENCAP
#define ETH_P_80211_ENCAP 0x890d /* TDLS comes under this category */
#endif
#ifndef ETH_P_PAE
#define ETH_P_PAE 0x888E /* Port Access Entity (IEEE 802.1X) */
#endif /* ETH_P_PAE */
#ifndef ETH_P_EAPOL
#define ETH_P_EAPOL ETH_P_PAE
#endif /* ETH_P_EAPOL */
#ifndef ETH_P_RSN_PREAUTH
#define ETH_P_RSN_PREAUTH 0x88c7
#endif /* ETH_P_RSN_PREAUTH */
#ifndef ETH_P_RRB
#define ETH_P_RRB 0x890D
#endif /* ETH_P_RRB */
#if 0 //#ifdef __GNUC__
#define PRINTF_FORMAT(a,b) __attribute__ ((format (printf, (a), (b))))
#define STRUCT_PACKED __attribute__ ((packed))
#else
#define PRINTF_FORMAT(a,b)
#define STRUCT_PACKED
#endif
#ifdef CONFIG_ANSI_C_EXTRA
#if !defined(_MSC_VER) || _MSC_VER < 1400
/* snprintf - used in number of places; sprintf() is _not_ a good replacement
* due to possible buffer overflow; see, e.g.,
* http://www.ijs.si/software/snprintf/ for portable implementation of
* snprintf. */
int snprintf(char *str, size_t size, const char *format, ...);
/* vsnprintf - only used for wpa_msg() in wpa_supplicant.c */
int vsnprintf(char *str, size_t size, const char *format, va_list ap);
#endif /* !defined(_MSC_VER) || _MSC_VER < 1400 */
/* getopt - only used in main.c */
int getopt(int argc, char *const argv[], const char *optstring);
extern char *optarg;
extern int optind;
#ifndef CONFIG_NO_SOCKLEN_T_TYPEDEF
#ifndef __socklen_t_defined
typedef int socklen_t;
#endif
#endif
/* inline - define as __inline or just define it to be empty, if needed */
#ifdef CONFIG_NO_INLINE
#define inline
#else
#define inline __inline
#endif
#ifndef __func__
#define __func__ "__func__ not defined"
#endif
#ifndef bswap_16
#define bswap_16(a) ((((u16) (a) << 8) & 0xff00) | (((u16) (a) >> 8) & 0xff))
#endif
#ifndef bswap_32
#define bswap_32(a) ((((u32) (a) << 24) & 0xff000000) | \
(((u32) (a) << 8) & 0xff0000) | \
(((u32) (a) >> 8) & 0xff00) | \
(((u32) (a) >> 24) & 0xff))
#endif
#ifndef MSG_DONTWAIT
#define MSG_DONTWAIT 0
#endif
#ifdef _WIN32_WCE
void perror(const char *s);
#endif /* _WIN32_WCE */
#endif /* CONFIG_ANSI_C_EXTRA */
#ifndef MAC2STR
#define MAC2STR(a) (a)[0], (a)[1], (a)[2], (a)[3], (a)[4], (a)[5]
#define MACSTR "%02x:%02x:%02x:%02x:%02x:%02x"
/*
* Compact form for string representation of MAC address
* To be used, e.g., for constructing dbus paths for P2P Devices
*/
#define COMPACT_MACSTR "%02x%02x%02x%02x%02x%02x"
#endif
#ifndef BIT
#define BIT(x) (1 << (x))
#endif
/*
* Definitions for sparse validation
* (http://kernel.org/pub/linux/kernel/people/josh/sparse/)
*/
#ifdef __CHECKER__
#define __force __attribute__((force))
#define __bitwise __attribute__((bitwise))
#else
#define __force
#define __bitwise
#endif
typedef u16 __bitwise be16;
typedef u16 __bitwise le16;
typedef u32 __bitwise be32;
typedef u32 __bitwise le32;
typedef u64 __bitwise be64;
typedef u64 __bitwise le64;
#ifndef __must_check
#if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 4)
#define __must_check __attribute__((__warn_unused_result__))
#else
#define __must_check
#endif /* __GNUC__ */
#endif /* __must_check */
//int hwaddr_aton(const char *txt, u8 *addr);
int hwaddr_compact_aton(const char *txt, u8 *addr);
int hwaddr_aton2(const char *txt, u8 *addr);
int hex2byte(const char *hex);
int hexstr2bin(const char *hex, u8 *buf, size_t len);
void inc_byte_array(u8 *counter, size_t len);
void wpa_get_ntp_timestamp(u8 *buf);
//int wpa_snprintf_hex(char *buf, size_t buf_size, const u8 *data, size_t len);
int wpa_snprintf_hex_uppercase(char *buf, size_t buf_size, const u8 *data,
size_t len);
#ifdef CONFIG_NATIVE_WINDOWS
void wpa_unicode2ascii_inplace(TCHAR *str);
TCHAR * wpa_strdup_tchar(const char *str);
#else /* CONFIG_NATIVE_WINDOWS */
#define wpa_unicode2ascii_inplace(s) do { } while (0)
#define wpa_strdup_tchar(s) strdup((s))
#endif /* CONFIG_NATIVE_WINDOWS */
void printf_encode(char *txt, size_t maxlen, const u8 *data, size_t len);
size_t printf_decode(u8 *buf, size_t maxlen, const char *str);
const char * wpa_ssid_txt(const u8 *ssid, size_t ssid_len);
char * wpa_config_parse_string(const char *value, size_t *len);
int is_hex(const u8 *data, size_t len);
size_t merge_byte_arrays(u8 *res, size_t res_len,
const u8 *src1, size_t src1_len,
const u8 *src2, size_t src2_len);
static inline int is_zero_ether_addr(const u8 *a)
{
return !(a[0] | a[1] | a[2] | a[3] | a[4] | a[5]);
}
static inline int is_broadcast_ether_addr(const u8 *a)
{
return (a[0] & a[1] & a[2] & a[3] & a[4] & a[5]) == 0xff;
}
#define broadcast_ether_addr (const u8 *) "\xff\xff\xff\xff\xff\xff"
#include "wpa_debug.h"
char * dup_binstr(const void *src, size_t len);
struct wpa_freq_range_list {
struct wpa_freq_range {
unsigned int min;
unsigned int max;
} *range;
unsigned int num;
};
int freq_range_list_parse(struct wpa_freq_range_list *res, const char *value);
int freq_range_list_includes(const struct wpa_freq_range_list *list,
unsigned int freq);
char * freq_range_list_str(const struct wpa_freq_range_list *list);
int int_array_len(const int *a);
void int_array_concat(int **res, const int *a);
void int_array_sort_unique(int *a);
void int_array_add_unique(int **res, int a);
#define ARRAY_SIZE(a) (sizeof(a) / sizeof((a)[0]))
void str_clear_free(char *str);
void bin_clear_free(void *bin, size_t len);
int random_mac_addr(u8 *addr);
int random_mac_addr_keep_oui(u8 *addr);
const char * cstr_token(const char *str, const char *delim, const char **last);
char * str_token(char *str, const char *delim, char **context);
size_t utf8_escape(const char *inp, size_t in_size,
char *outp, size_t out_size);
size_t utf8_unescape(const char *inp, size_t in_size,
char *outp, size_t out_size);
int is_ctrl_char(char c);
#ifndef bswap_16
#define bswap_16(a) ((((u16) (a) << 8) & 0xff00) | (((u16) (a) >> 8) & 0xff))
#endif
/*
* gcc 4.4 ends up generating strict-aliasing warnings about some very common
* networking socket uses that do not really result in a real problem and
* cannot be easily avoided with union-based type-punning due to struct
* definitions including another struct in system header files. To avoid having
* to fully disable strict-aliasing warnings, provide a mechanism to hide the
* typecast from aliasing for now. A cleaner solution will hopefully be found
* in the future to handle these cases.
*/
void * __hide_aliasing_typecast(void *foo);
#define aliasing_hide_typecast(a,t) (t *) __hide_aliasing_typecast((a))
#ifdef CONFIG_VALGRIND
#include <valgrind/memcheck.h>
#define WPA_MEM_DEFINED(ptr, len) VALGRIND_MAKE_MEM_DEFINED((ptr), (len))
#else /* CONFIG_VALGRIND */
#define WPA_MEM_DEFINED(ptr, len) do { } while (0)
#endif /* CONFIG_VALGRIND */
#endif /* COMMON_H */

View File

@@ -0,0 +1,119 @@
#ifndef INCLUDES_H
#define INCLUDES_H
#define CONFIG_NO_STDOUT_DEBUG
#ifndef CONFIG_NO_STDOUT_DEBUG
/* Event messages with fixed prefix */
/** Authentication completed successfully and data connection enabled */
#define WPA_EVENT_CONNECTED "CTRL-EVENT-CONNECTED "
/** Disconnected, data connection is not available */
#define WPA_EVENT_DISCONNECTED "CTRL-EVENT-DISCONNECTED "
/** Association rejected during connection attempt */
#define WPA_EVENT_ASSOC_REJECT "CTRL-EVENT-ASSOC-REJECT "
/** Authentication rejected during connection attempt */
#define WPA_EVENT_AUTH_REJECT "CTRL-EVENT-AUTH-REJECT "
/** wpa_supplicant is exiting */
#define WPA_EVENT_TERMINATING "CTRL-EVENT-TERMINATING "
/** Password change was completed successfully */
#define WPA_EVENT_PASSWORD_CHANGED "CTRL-EVENT-PASSWORD-CHANGED "
/** EAP-Request/Notification received */
#define WPA_EVENT_EAP_NOTIFICATION "CTRL-EVENT-EAP-NOTIFICATION "
/** EAP authentication started (EAP-Request/Identity received) */
#define WPA_EVENT_EAP_STARTED "CTRL-EVENT-EAP-STARTED "
/** EAP method proposed by the server */
#define WPA_EVENT_EAP_PROPOSED_METHOD "CTRL-EVENT-EAP-PROPOSED-METHOD "
/** EAP method selected */
#define WPA_EVENT_EAP_METHOD "CTRL-EVENT-EAP-METHOD "
/** EAP peer certificate from TLS */
#define WPA_EVENT_EAP_PEER_CERT "CTRL-EVENT-EAP-PEER-CERT "
/** EAP peer certificate alternative subject name component from TLS */
#define WPA_EVENT_EAP_PEER_ALT "CTRL-EVENT-EAP-PEER-ALT "
/** EAP TLS certificate chain validation error */
#define WPA_EVENT_EAP_TLS_CERT_ERROR "CTRL-EVENT-EAP-TLS-CERT-ERROR "
/** EAP status */
#define WPA_EVENT_EAP_STATUS "CTRL-EVENT-EAP-STATUS "
/** EAP authentication completed successfully */
#define WPA_EVENT_EAP_SUCCESS "CTRL-EVENT-EAP-SUCCESS "
/** EAP authentication failed (EAP-Failure received) */
#define WPA_EVENT_EAP_FAILURE "CTRL-EVENT-EAP-FAILURE "
/** Network block temporarily disabled (e.g., due to authentication failure) */
#define WPA_EVENT_TEMP_DISABLED "CTRL-EVENT-SSID-TEMP-DISABLED "
/** Temporarily disabled network block re-enabled */
#define WPA_EVENT_REENABLED "CTRL-EVENT-SSID-REENABLED "
/** New scan started */
#define WPA_EVENT_SCAN_STARTED "CTRL-EVENT-SCAN-STARTED "
/** New scan results available */
#define WPA_EVENT_SCAN_RESULTS "CTRL-EVENT-SCAN-RESULTS "
/** Scan command failed */
#define WPA_EVENT_SCAN_FAILED "CTRL-EVENT-SCAN-FAILED "
/** wpa_supplicant state change */
#define WPA_EVENT_STATE_CHANGE "CTRL-EVENT-STATE-CHANGE "
/** A new BSS entry was added (followed by BSS entry id and BSSID) */
#define WPA_EVENT_BSS_ADDED "CTRL-EVENT-BSS-ADDED "
/** A BSS entry was removed (followed by BSS entry id and BSSID) */
#define WPA_EVENT_BSS_REMOVED "CTRL-EVENT-BSS-REMOVED "
/** No suitable network was found */
#define WPA_EVENT_NETWORK_NOT_FOUND "CTRL-EVENT-NETWORK-NOT-FOUND "
/** Change in the signal level was reported by the driver */
#define WPA_EVENT_SIGNAL_CHANGE "CTRL-EVENT-SIGNAL-CHANGE "
/** Regulatory domain channel */
#define WPA_EVENT_REGDOM_CHANGE "CTRL-EVENT-REGDOM-CHANGE "
/** RSN IBSS 4-way handshakes completed with specified peer */
#define IBSS_RSN_COMPLETED "IBSS-RSN-COMPLETED "
/** Notification of frequency conflict due to a concurrent operation.
*
* The indicated network is disabled and needs to be re-enabled before it can
* be used again.
*/
#define WPA_EVENT_FREQ_CONFLICT "CTRL-EVENT-FREQ-CONFLICT "
/** Frequency ranges that the driver recommends to avoid */
#define WPA_EVENT_AVOID_FREQ "CTRL-EVENT-AVOID-FREQ "
/** WPS overlap detected in PBC mode */
#define WPS_EVENT_OVERLAP "WPS-OVERLAP-DETECTED "
/** Available WPS AP with active PBC found in scan results */
#define WPS_EVENT_AP_AVAILABLE_PBC "WPS-AP-AVAILABLE-PBC "
/** Available WPS AP with our address as authorized in scan results */
#define WPS_EVENT_AP_AVAILABLE_AUTH "WPS-AP-AVAILABLE-AUTH "
/** Available WPS AP with recently selected PIN registrar found in scan results
*/
#define WPS_EVENT_AP_AVAILABLE_PIN "WPS-AP-AVAILABLE-PIN "
/** Available WPS AP found in scan results */
#define WPS_EVENT_AP_AVAILABLE "WPS-AP-AVAILABLE "
/** A new credential received */
#define WPS_EVENT_CRED_RECEIVED "WPS-CRED-RECEIVED "
/** M2D received */
#define WPS_EVENT_M2D "WPS-M2D "
/** WPS registration failed after M2/M2D */
#define WPS_EVENT_FAIL "WPS-FAIL "
/** WPS registration completed successfully */
#define WPS_EVENT_SUCCESS "WPS-SUCCESS "
/** WPS enrollment attempt timed out and was terminated */
#define WPS_EVENT_TIMEOUT "WPS-TIMEOUT "
/* PBC mode was activated */
#define WPS_EVENT_ACTIVE "WPS-PBC-ACTIVE "
/* PBC mode was disabled */
#define WPS_EVENT_DISABLE "WPS-PBC-DISABLE "
#define WPS_EVENT_ENROLLEE_SEEN "WPS-ENROLLEE-SEEN "
#define WPS_EVENT_OPEN_NETWORK "WPS-OPEN-NETWORK "
/* WPS ER events */
#define WPS_EVENT_ER_AP_ADD "WPS-ER-AP-ADD "
#define WPS_EVENT_ER_AP_REMOVE "WPS-ER-AP-REMOVE "
#define WPS_EVENT_ER_ENROLLEE_ADD "WPS-ER-ENROLLEE-ADD "
#define WPS_EVENT_ER_ENROLLEE_REMOVE "WPS-ER-ENROLLEE-REMOVE "
#define WPS_EVENT_ER_AP_SETTINGS "WPS-ER-AP-SETTINGS "
#define WPS_EVENT_ER_SET_SEL_REG "WPS-ER-AP-SET-SEL-REG "
#endif /* CONFIG_NO_STDOUT_DEBUG */
//#define DBG_871X(...) vTaskDelay(100)
//DBG_871X_LEVEL(_drv_always_, "no beacon for a long time, disconnect or roaming\n");
//#define DBG_871X(...) DBG_871X_LEVEL(_drv_always_,...)
#endif /* INCLUDES_H */

View File

@@ -0,0 +1,599 @@
/*
* OS specific functions
* Copyright (c) 2005-2009, Jouni Malinen <j@w1.fi>
*
* This software may be distributed under the terms of the BSD license.
* See README for more details.
*/
#ifndef OS_H
#define OS_H
//#include "basic_types.h"
#include <autoconf.h>
#include "osdep_service.h"
//#include "freertos/wrapper.h"
#include "utils/rom/rom_wps_os.h"
typedef void* xqueue_handle_t;
typedef long os_time_t;
typedef _timer os_timer;
/**
* os_sleep - Sleep (sec, usec)
* @sec: Number of seconds to sleep
* @usec: Number of microseconds to sleep
*/
void os_sleep(os_time_t sec, os_time_t usec);
struct os_time {
os_time_t sec;
os_time_t usec;
};
struct os_reltime {
os_time_t sec;
os_time_t usec;
};
/**
* os_get_time - Get current time (sec, usec)
* @t: Pointer to buffer for the time
* Returns: 0 on success, -1 on failure
*/
int os_get_time(struct os_time *t);
int os_get_reltime(struct os_reltime *t);
/* Helper macros for handling struct os_time */
/* (&timeout->time, &tmp->time) */
#define os_time_before(a, b) \
((a)->sec < (b)->sec || \
((a)->sec == (b)->sec && (a)->usec < (b)->usec))
#define os_time_sub(a, b, res) do { \
(res)->sec = (a)->sec - (b)->sec; \
(res)->usec = (a)->usec - (b)->usec; \
if ((res)->usec < 0) { \
(res)->sec--; \
(res)->usec += 1000000; \
} \
} while (0)
/**
* os_mktime - Convert broken-down time into seconds since 1970-01-01
* @year: Four digit year
* @month: Month (1 .. 12)
* @day: Day of month (1 .. 31)
* @hour: Hour (0 .. 23)
* @min: Minute (0 .. 59)
* @sec: Second (0 .. 60)
* @t: Buffer for returning calendar time representation (seconds since
* 1970-01-01 00:00:00)
* Returns: 0 on success, -1 on failure
*
* Note: The result is in seconds from Epoch, i.e., in UTC, not in local time
* which is used by POSIX mktime().
*/
int os_mktime(int year, int month, int day, int hour, int min, int sec,
os_time_t *t);
struct os_tm {
int sec; /* 0..59 or 60 for leap seconds */
int min; /* 0..59 */
int hour; /* 0..23 */
int day; /* 1..31 */
int month; /* 1..12 */
int year; /* Four digit year */
};
int os_gmtime(os_time_t t, struct os_tm *tm);
/* Helpers for handling struct os_time */
/* Helpers for handling struct os_reltime */
static inline int os_reltime_before(struct os_reltime *a,
struct os_reltime *b)
{
return os_time_before(a,b);
}
static inline void os_reltime_sub(struct os_reltime *a, struct os_reltime *b,
struct os_reltime *res)
{
os_time_sub(a,b,res);
}
static inline void os_reltime_age(struct os_reltime *start,
struct os_reltime *age)
{
struct os_reltime now;
os_get_time((struct os_time *)&now);
os_reltime_sub(&now, start, age);
}
static inline int os_reltime_expired(struct os_reltime *now,
struct os_reltime *ts,
os_time_t timeout_secs)
{
struct os_reltime age;
os_reltime_sub(now, ts, &age);
return (age.sec > timeout_secs) ||
(age.sec == timeout_secs && age.usec > 0);
}
/**
* os_daemonize - Run in the background (detach from the controlling terminal)
* @pid_file: File name to write the process ID to or %NULL to skip this
* Returns: 0 on success, -1 on failure
*/
int os_daemonize(const char *pid_file);
/**
* os_daemonize_terminate - Stop running in the background (remove pid file)
* @pid_file: File name to write the process ID to or %NULL to skip this
*/
void os_daemonize_terminate(const char *pid_file);
/**
* os_get_random - Get cryptographically strong pseudo random data
* @buf: Buffer for pseudo random data
* @len: Length of the buffer
* Returns: 0 on success, -1 on failure
*/
int os_get_random(unsigned char *buf, size_t len);
/**
* os_random - Get pseudo random value (not necessarily very strong)
* Returns: Pseudo random value
*/
unsigned long os_random(void);
/**
* os_rel2abs_path - Get an absolute path for a file
* @rel_path: Relative path to a file
* Returns: Absolute path for the file or %NULL on failure
*
* This function tries to convert a relative path of a file to an absolute path
* in order for the file to be found even if current working directory has
* changed. The returned value is allocated and caller is responsible for
* freeing it. It is acceptable to just return the same path in an allocated
* buffer, e.g., return strdup(rel_path). This function is only used to find
* configuration files when os_daemonize() may have changed the current working
* directory and relative path would be pointing to a different location.
*/
char * os_rel2abs_path(const char *rel_path);
/**
* os_program_init - Program initialization (called at start)
* Returns: 0 on success, -1 on failure
*
* This function is called when a programs starts. If there are any OS specific
* processing that is needed, it can be placed here. It is also acceptable to
* just return 0 if not special processing is needed.
*/
int os_program_init(void);
/**
* os_program_deinit - Program deinitialization (called just before exit)
*
* This function is called just before a program exists. If there are any OS
* specific processing, e.g., freeing resourced allocated in os_program_init(),
* it should be done here. It is also acceptable for this function to do
* nothing.
*/
void os_program_deinit(void);
/**
* os_setenv - Set environment variable
* @name: Name of the variable
* @value: Value to set to the variable
* @overwrite: Whether existing variable should be overwritten
* Returns: 0 on success, -1 on error
*
* This function is only used for wpa_cli action scripts. OS wrapper does not
* need to implement this if such functionality is not needed.
*/
int os_setenv(const char *name, const char *value, int overwrite);
/**
* os_unsetenv - Delete environent variable
* @name: Name of the variable
* Returns: 0 on success, -1 on error
*
* This function is only used for wpa_cli action scripts. OS wrapper does not
* need to implement this if such functionality is not needed.
*/
int os_unsetenv(const char *name);
/**
* os_readfile - Read a file to an allocated memory buffer
* @name: Name of the file to read
* @len: For returning the length of the allocated buffer
* Returns: Pointer to the allocated buffer or %NULL on failure
*
* This function allocates memory and reads the given file to this buffer. Both
* binary and text files can be read with this function. The caller is
* responsible for freeing the returned buffer with os_free().
*/
char * os_readfile(const char *name, size_t *len);
//#if 0
/**
* os_zalloc - Allocate and zero memory
* @size: Number of bytes to allocate
* Returns: Pointer to allocated and zeroed memory or %NULL on failure
*
* Caller is responsible for freeing the returned buffer with os_free().
*/
void * os_zalloc(size_t size);
/**
* os_calloc - Allocate and zero memory for an array
* @nmemb: Number of members in the array
* @size: Number of bytes in each member
* Returns: Pointer to allocated and zeroed memory or %NULL on failure
*
* This function can be used as a wrapper for os_zalloc(nmemb * size) when an
* allocation is used for an array. The main benefit over os_zalloc() is in
* having an extra check to catch integer overflows in multiplication.
*
* Caller is responsible for freeing the returned buffer with os_free().
*/
static inline void * os_calloc(size_t nmemb, size_t size)
{
if (size && nmemb > (~(size_t) 0) / size)
return NULL;
return os_zalloc(nmemb * size);
}
//#endif
static inline int os_memcmp_const(const void *a, const void *b, size_t len)
{
const u8 *aa = a;
const u8 *bb = b;
size_t i;
u8 res;
for (res = 0, i = 0; i < len; i++)
res |= aa[i] ^ bb[i];
return res;
}
/*
* The following functions are wrapper for standard ANSI C or POSIX functions.
* By default, they are just defined to use the standard function name and no
* os_*.c implementation is needed for them. This avoids extra function calls
* by allowing the C pre-processor take care of the function name mapping.
*
* If the target system uses a C library that does not provide these functions,
* build_config.h can be used to define the wrappers to use a different
* function name. This can be done on function-by-function basis since the
* defines here are only used if build_config.h does not define the os_* name.
* If needed, os_*.c file can be used to implement the functions that are not
* included in the C library on the target system. Alternatively,
* OS_NO_C_LIB_DEFINES can be defined to skip all defines here in which case
* these functions need to be implemented in os_*.c file for the target system.
*/
#ifdef OS_NO_C_LIB_DEFINES
/**
* os_malloc - Allocate dynamic memory
* @size: Size of the buffer to allocate
* Returns: Allocated buffer or %NULL on failure
*
* Caller is responsible for freeing the returned buffer with os_free().
*/
void * os_malloc(size_t size);
/**
* os_realloc - Re-allocate dynamic memory
* @ptr: Old buffer from os_malloc() or os_realloc()
* @size: Size of the new buffer
* Returns: Allocated buffer or %NULL on failure
*
* Caller is responsible for freeing the returned buffer with os_free().
* If re-allocation fails, %NULL is returned and the original buffer (ptr) is
* not freed and caller is still responsible for freeing it.
*/
void * os_realloc(void *ptr, size_t size);
/**
* os_free - Free dynamic memory
* @ptr: Old buffer from os_malloc() or os_realloc(); can be %NULL
*/
void os_free(void *ptr);
/**
* os_memcpy - Copy memory area
* @dest: Destination
* @src: Source
* @n: Number of bytes to copy
* Returns: dest
*
* The memory areas src and dst must not overlap. os_memmove() can be used with
* overlapping memory.
*/
void * os_memcpy(void *dest, const void *src, size_t n);
/**
* os_memmove - Copy memory area
* @dest: Destination
* @src: Source
* @n: Number of bytes to copy
* Returns: dest
*
* The memory areas src and dst may overlap.
*/
void *os_memmove(void *dest, const void *src, size_t n);
/**
* os_memset - Fill memory with a constant byte
* @s: Memory area to be filled
* @c: Constant byte
* @n: Number of bytes started from s to fill with c
* Returns: s
*/
void *os_memset(void *s, int c, size_t n);
/**
* os_memcmp - Compare memory areas
* @s1: First buffer
* @s2: Second buffer
* @n: Maximum numbers of octets to compare
* Returns: An integer less than, equal to, or greater than zero if s1 is
* found to be less than, to match, or be greater than s2. Only first n
* characters will be compared.
*/
int os_memcmp(const void *s1, const void *s2, size_t n);
/**
* os_strdup - Duplicate a string
* @s: Source string
* Returns: Allocated buffer with the string copied into it or %NULL on failure
*
* Caller is responsible for freeing the returned buffer with os_free().
*/
char *os_strdup(const char *s);
/**
* os_strlen - Calculate the length of a string
* @s: '\0' terminated string
* Returns: Number of characters in s (not counting the '\0' terminator)
*/
size_t os_strlen(const char *s);
/**
* os_strcasecmp - Compare two strings ignoring case
* @s1: First string
* @s2: Second string
* Returns: An integer less than, equal to, or greater than zero if s1 is
* found to be less than, to match, or be greatred than s2
*/
int os_strcasecmp(const char *s1, const char *s2);
/**
* os_strncasecmp - Compare two strings ignoring case
* @s1: First string
* @s2: Second string
* @n: Maximum numbers of characters to compare
* Returns: An integer less than, equal to, or greater than zero if s1 is
* found to be less than, to match, or be greater than s2. Only first n
* characters will be compared.
*/
int os_strncasecmp(const char *s1, const char *s2, size_t n);
/**
* os_strchr - Locate the first occurrence of a character in string
* @s: String
* @c: Character to search for
* Returns: Pointer to the matched character or %NULL if not found
*/
char *os_strchr(const char *s, int c);
/**
* os_strrchr - Locate the last occurrence of a character in string
* @s: String
* @c: Character to search for
* Returns: Pointer to the matched character or %NULL if not found
*/
char *os_strrchr(const char *s, int c);
/**
* os_strcmp - Compare two strings
* @s1: First string
* @s2: Second string
* Returns: An integer less than, equal to, or greater than zero if s1 is
* found to be less than, to match, or be greatred than s2
*/
int os_strcmp(const char *s1, const char *s2);
/**
* os_strncmp - Compare two strings
* @s1: First string
* @s2: Second string
* @n: Maximum numbers of characters to compare
* Returns: An integer less than, equal to, or greater than zero if s1 is
* found to be less than, to match, or be greater than s2. Only first n
* characters will be compared.
*/
int os_strncmp(const char *s1, const char *s2, size_t n);
/**
* os_strncpy - Copy a string
* @dest: Destination
* @src: Source
* @n: Maximum number of characters to copy
* Returns: dest
*/
char *os_strncpy(char *dest, const char *src, size_t n);
/**
* os_strstr - Locate a substring
* @haystack: String (haystack) to search from
* @needle: Needle to search from haystack
* Returns: Pointer to the beginning of the substring or %NULL if not found
*/
char *os_strstr(const char *haystack, const char *needle);
/**
* os_snprintf - Print to a memory buffer
* @str: Memory buffer to print into
* @size: Maximum length of the str buffer
* @format: printf format
* Returns: Number of characters printed (not including trailing '\0').
*
* If the output buffer is truncated, number of characters which would have
* been written is returned. Since some C libraries return -1 in such a case,
* the caller must be prepared on that value, too, to indicate truncation.
*
* Note: Some C library implementations of snprintf() may not guarantee null
* termination in case the output is truncated. The OS wrapper function of
* os_snprintf() should provide this guarantee, i.e., to null terminate the
* output buffer if a C library version of the function is used and if that
* function does not guarantee null termination.
*
* If the target system does not include snprintf(), see, e.g.,
* http://www.ijs.si/software/snprintf/ for an example of a portable
* implementation of snprintf.
*/
int os_snprintf(char *str, size_t size, const char *format, ...);
#else /* OS_NO_C_LIB_DEFINES */
#if !defined(CONFIG_PLATFORM_8195A) && !defined(CONFIG_PLATFORM_8711B)
#ifdef CONFIG_MEM_MONITOR
u8* os_malloc(u32 sz);
void os_mfree(u8 *pbuf, u32 sz);
#ifndef os_free
#define os_free(p, sz) os_mfree(((u8*)(p)), (sz))
#endif
#else
#ifndef os_malloc
#define os_malloc(sz) _rtw_malloc(sz)
#endif
#ifndef os_free
#define os_free(p, sz) _rtw_mfree(((u8*)(p)), (sz))
#endif
#endif
#endif
extern void *os_zalloc(size_t size);
extern char *os_strdup(const char *string_copy_from);
#ifndef os_sleep
#define os_sleep(s, us) rtw_mdelay_os((s)*1000 + (us)/1000)
#endif
#ifndef os_memcpy
#define os_memcpy(d, s, n) rtw_memcpy((void*)(d), ((void*)(s)), (n))
#endif
#ifndef os_memmove
#define os_memmove(d, s, n) memmove((d), (s), (n))
#endif
#ifndef os_memset
#define os_memset(pbuf, c, sz) rtw_memset(pbuf, c, sz)
#endif
#ifndef os_memcmp
#define os_memcmp(s1, s2, n) rtw_memcmp(((void*)(s1)), ((void*)(s2)), (n))
#endif
#ifndef os_memcmp_p2p
#define os_memcmp_p2p(s1, s2, n) memcmp((s1), (s2), (n))
#endif
#ifndef os_get_random_bytes
#define os_get_random_bytes(d,sz) rtw_get_random_bytes(((void*)(d)), (sz))
#endif
#ifndef os_strlen
#define os_strlen(s) strlen(s)
#endif
#ifndef os_strcasecmp
#ifdef _MSC_VER
#define os_strcasecmp(s1, s2) _stricmp((s1), (s2))
#else
#define os_strcasecmp(s1, s2) strcasecmp((s1), (s2))
#endif
#endif
#ifndef os_strncasecmp
#ifdef _MSC_VER
#define os_strncasecmp(s1, s2, n) _strnicmp((s1), (s2), (n))
#else
#define os_strncasecmp(s1, s2, n) strncasecmp((s1), (s2), (n))
#endif
#endif
#ifndef os_init_timer
#define os_init_timer(t, p, f, x, n) rtw_init_timer((t), (p), (f), (x), (n))
#endif
#ifndef os_set_timer
#define os_set_timer(t, d) rtw_set_timer((t), (d))
#endif
#ifndef os_cancel_timer
#define os_cancel_timer(t) rtw_cancel_timer(t)
#endif
#ifndef os_del_timer
#define os_del_timer(t) rtw_del_timer(t)
#endif
#ifndef os_atoi
#define os_atoi(s) rtw_atoi(s)
#endif
#ifndef os_strchr
#define os_strchr(s, c) strchr((s), (c))
#endif
#ifndef os_strcmp
#define os_strcmp(s1, s2) strcmp((s1), (s2))
#endif
#ifndef os_strncmp
#define os_strncmp(s1, s2, n) strncmp((s1), (s2), (n))
#endif
#ifndef os_strncpy
#define os_strncpy(d, s, n) strncpy((d), (s), (n))
#endif
#ifndef os_strrchr
#define os_strrchr(s, c) strrchr((s), (c))
#endif
#ifndef os_strstr
#define os_strstr(h, n) strstr((h), (n))
#endif
#ifndef os_snprintf
#ifdef _MSC_VER
#define os_snprintf _snprintf
#else
#define os_snprintf snprintf
#endif
#endif
#endif /* OS_NO_C_LIB_DEFINES */
static inline void * os_realloc_array(void *ptr, size_t nmemb, size_t size)
{
if (size && nmemb > (~(size_t) 0) / size)
return NULL;
if(ptr == NULL){
return os_malloc(nmemb * size);
}
else{
return os_realloc(ptr, nmemb * size, nmemb * size);
}
}
void *os_xqueue_create(unsigned long uxQueueLength, unsigned long uxItemSize) ;
int os_xqueue_receive(xqueue_handle_t xQueue, void * const pvBuffer, unsigned long xSecsToWait);
void os_xqueue_delete(xqueue_handle_t xQueue );
int os_xqueue_send(xqueue_handle_t xQueue, const void * const pvItemToQueue, unsigned long xSecsToWait);
#endif /* OS_H */

View File

@@ -0,0 +1,119 @@
/*
* OS specific functions for UNIX/POSIX systems
* Copyright (c) 2005-2009, Jouni Malinen <j@w1.fi>
*
* This software may be distributed under the terms of the BSD license.
* See README for more details.
*/
#include "utils/os.h"
//#ifdef CONFIG_WPS
#if !defined(CONFIG_PLATFORM_8195A) && !defined(CONFIG_PLATFORM_8711B)
#ifdef CONFIG_MEM_MONITOR
#if CONFIG_MEM_MONITOR & MEM_MONITOR_LEAK
_list wpa_mem_table;
int wpa_mem_used_num;
//int wpa_mem_used_size;
#endif
extern int min_free_heap_size;
u8* os_malloc(u32 sz)
{
int free_heap_size = rtw_getFreeHeapSize();
u8 *pbuf = _rtw_malloc(sz);
#if CONFIG_MEM_MONITOR & MEM_MONITOR_LEAK
add_mem_usage(&wpa_mem_table, pbuf, sz, &wpa_mem_used_num, MEM_MONITOR_FLAG_WPAS);
#else
add_mem_usage(NULL, pbuf, sz, NULL, MEM_MONITOR_FLAG_WPAS);
#endif
if(min_free_heap_size > free_heap_size)
min_free_heap_size = free_heap_size;
return pbuf;
}
void os_mfree(u8 *pbuf, u32 sz)
{
_rtw_mfree(pbuf, sz);
#if CONFIG_MEM_MONITOR & MEM_MONITOR_LEAK
del_mem_usage(&wpa_mem_table, pbuf, &wpa_mem_used_num, MEM_MONITOR_FLAG_WPAS);
#else
del_mem_usage(NULL, pbuf, NULL, MEM_MONITOR_FLAG_WPAS);
#endif
}
#endif//CONFIG_MEM_MONITOR
#endif// !defined(CONFIG_PLATFORM_8195A)
#ifndef OS_NO_C_LIB_DEFINES
char *os_strdup(const char *string_copy_from)
{
char *string_copy_to = NULL;
string_copy_to = os_zalloc(strlen(string_copy_from) + 1);
os_memcpy((void *)string_copy_to, string_copy_from, strlen(string_copy_from));
string_copy_to[strlen(string_copy_from)] = '\0';
return string_copy_to;
}
#endif
int os_get_random(unsigned char *buf, size_t len)
{
//TODO implement it
rtw_get_random_bytes(buf, len);
return 0;
}
int os_get_time(struct os_time *t){
unsigned int tt = rtw_get_current_time();
t->sec = (os_time_t) (tt / 1000);
t->usec = (os_time_t) (tt % 1000)*1000;
return 0;
}
int os_get_reltime(struct os_reltime *t){
os_get_time((struct os_time *)t);
return 0;
}
#if 0
void *os_xqueue_create(unsigned long uxQueueLength, unsigned long uxItemSize)
{
return xQueueCreate( uxQueueLength, uxItemSize );
}
int os_xqueue_receive(xqueue_handle_t xQueue, void * const pvBuffer, unsigned long xSecsToWait)
{
return xQueueReceive((xQueueHandle)xQueue, pvBuffer, (portTickType)(xSecsToWait*configTICK_RATE_HZ));
}
void os_xqueue_delete(xqueue_handle_t xQueue )
{
vQueueDelete((xQueueHandle)xQueue);
}
int os_xqueue_send(xqueue_handle_t xQueue, const void * const pvItemToQueue, unsigned long xSecsToWait)
{
return xQueueSendToBack((xQueueHandle)xQueue, pvItemToQueue, (portTickType)(xSecsToWait*configTICK_RATE_HZ));
}
#else
void *os_xqueue_create(unsigned long uxQueueLength, unsigned long uxItemSize)
{
void* xQueue = NULL;
rtw_init_xqueue(&xQueue, "queue", uxItemSize, uxQueueLength);
return xQueue;
}
int os_xqueue_receive(xqueue_handle_t xQueue, void * const pvBuffer, unsigned long xSecsToWait)
{
return rtw_pop_from_xqueue(&xQueue, pvBuffer, xSecsToWait*1000);
}
void os_xqueue_delete(xqueue_handle_t xQueue )
{
rtw_deinit_xqueue(&xQueue);
}
int os_xqueue_send(xqueue_handle_t xQueue, const void * const pvItemToQueue, unsigned long xSecsToWait)
{
return rtw_push_to_xqueue(&xQueue, (void*)pvItemToQueue, xSecsToWait*1000);
}
#endif
//#endif

View File

@@ -0,0 +1,24 @@
/*
* OS specific functions
* Copyright (c) 2005-2009, Jouni Malinen <j@w1.fi>
*
* This software may be distributed under the terms of the BSD license.
* See README for more details.
*/
#ifndef ROM_WPS_OS_H
#define ROM_WPS_OS_H
#if defined(CONFIG_PLATFORM_8195A) || defined(CONFIG_PLATFORM_8711B)
#include <rom_wlan_ram_map.h>
extern struct _rom_wlan_ram_map rom_wlan_ram_map;
#define os_malloc(sz) rom_wlan_ram_map.rtw_malloc(sz)
#define os_free(p, sz) rom_wlan_ram_map.rtw_mfree(((u8*)(p)), (sz))
#endif
extern u8 *WPS_realloc(u8 *old_buf, u32 old_sz, u32 new_sz);
#define os_realloc(p, os, ns) WPS_realloc(((u8*)(p)),(os),(ns))
#endif /* ROM_WPS_OS_H */

View File

@@ -0,0 +1,31 @@
/*
* Universally Unique IDentifier (UUID)
* Copyright (c) 2008, Jouni Malinen <j@w1.fi>
*
* This software may be distributed under the terms of the BSD license.
* See README for more details.
*/
#ifndef UUID_H
#define UUID_H
#include <platform/platform_stdlib.h>
#define UUID_LEN 16
int uuid_str2bin(const char *str, u8 *bin);
static int uuid_bin2str(const u8 *bin, char *str, size_t max_len)
{
int len;
len = os_snprintf(str, max_len, "%02x%02x%02x%02x-%02x%02x-%02x%02x-"
"%02x%02x-%02x%02x%02x%02x%02x%02x",
bin[0], bin[1], bin[2], bin[3],
bin[4], bin[5], bin[6], bin[7],
bin[8], bin[9], bin[10], bin[11],
bin[12], bin[13], bin[14], bin[15]);
if (len < 0 || (size_t) len >= max_len)
return -1;
return 0;
}
int is_nil_uuid(const u8 *uuid);
#endif /* UUID_H */

View File

@@ -0,0 +1,79 @@
/*
* wpa_supplicant/hostapd / Debug prints
* Copyright (c) 2002-2007, Jouni Malinen <j@w1.fi>
*
* This software may be distributed under the terms of the BSD license.
* See README for more details.
*/
#ifndef WPA_DEBUG_H
#define WPA_DEBUG_H
#include "utils/wpabuf.h"
/* Debugging function - conditional printf and hex dump. Driver wrappers can
* use these for debugging purposes. */
enum {
MSG_EXCESSIVE, MSG_MSGDUMP, MSG_DEBUG, MSG_INFO, MSG_ALWAYS, MSG_WARNING, MSG_ERROR
};
#define wpa_debug_print_timestamp() do { } while (0)
#define wpa_hexdump(l,t,b,le) do { } while (0)
#define wpa_hexdump_buf_key(l,t,b) do { } while (0)
#define wpa_hexdump_ascii_key(l,t,b,le) do { } while (0)
#define wpa_debug_open_file(p) do { } while (0)
#define wpa_debug_close_file() do { } while (0)
#define wpa_dbg(args...) do { } while (0)
#define wpa_msg_ctrl(args...) do { } while (0)
#define wpa_msg_register_cb(f) do { } while (0)
#define wpa_msg_register_ifname_cb(f) do { } while (0)
static inline int wpa_debug_reopen_file(void)
{
return 0;
}
#define wprintf(fmt, arg...) printf("[%d] "fmt, rtw_get_current_time(),##arg)
#ifdef CONFIG_NO_STDOUT_DEBUG
#define wpa_printf(args...) do { } while (0)
#define wpa_hexdump_buf(l,t,b) do { } while (0)
#define wpa_hexdump_key(l,t,b,le) do { } while (0)
#define wpa_hexdump_ascii(l,t,b,le) do { } while (0)
#define wpa_msg(args...) do { } while (0)
#else
//void wpa_printf(int level, const char *fmt, ...);
#define wpa_printf(level, fmt, arg...) \
do {\
if (level >= MSG_INFO) {\
{\
printf("\r\n%d:", rtw_get_current_time());\
printf(fmt, ##arg);\
printf("\n\r");\
} \
}\
}while(0)
#define wpa_msg(ctx,level,fmt,arg...) wpa_printf((level),(fmt), ##arg)
void wpa_hexdump_key(int level, const char *title, const void *buf, size_t len);
void wpa_hexdump_buf(int level, const char *title,
const struct wpabuf *buf);
void wpa_hexdump_ascii(int level, const char *title, const void *buf,
size_t len);
#ifdef EAPOL_TEST
#define WPA_ASSERT(a) \
do { \
if (!(a)) { \
printf("WPA_ASSERT FAILED '" #a "' " \
"%s %s:%d\n", \
__FUNCTION__, __FILE__, __LINE__); \
exit(1); \
} \
} while (0)
#else
#define WPA_ASSERT(a) do { } while (0)
#endif
#endif //CONFIG_NO_STDOUT_DEBUG
#endif /* WPA_DEBUG_H */

View File

@@ -0,0 +1,188 @@
/*
* Dynamic data buffer
* Copyright (c) 2007-2012, Jouni Malinen <j@w1.fi>
*
* This software may be distributed under the terms of the BSD license.
* See README for more details.
*/
#ifndef WPABUF_H
#define WPABUF_H
/* wpabuf::buf is a pointer to external data */
#define WPABUF_FLAG_EXT_DATA BIT(0)
/*
* Internal data structure for wpabuf. Please do not touch this directly from
* elsewhere. This is only defined in header file to allow inline functions
* from this file to access data.
*/
struct wpabuf {
size_t size; /* total size of the allocated buffer (i.e allocated buffer size)*/
size_t used; /* length of data in the buffer (i.e data length) */
u8 *buf; /* pointer to the head of the buffer (i.e buffer address) */
unsigned int flags;
/* optionally followed by the allocated buffer */
};
int wpabuf_resize(struct wpabuf **buf, size_t add_len);
struct wpabuf * wpabuf_alloc(size_t len);
struct wpabuf * wpabuf_alloc_ext_data(u8 *data, size_t len);
struct wpabuf * wpabuf_alloc_copy(const void *data, size_t len);
struct wpabuf * wpabuf_dup(const struct wpabuf *src);
void wpabuf_free(struct wpabuf *buf);
void * wpabuf_put(struct wpabuf *buf, size_t len);
struct wpabuf * wpabuf_concat(struct wpabuf *a, struct wpabuf *b);
struct wpabuf * wpabuf_zeropad(struct wpabuf *buf, size_t len);
void wpabuf_printf(struct wpabuf *buf, char *fmt, ...) PRINTF_FORMAT(2, 3);
/**
* wpabuf_size - Get the currently allocated size of a wpabuf buffer
* @buf: wpabuf buffer
* Returns: Currently allocated size of the buffer
*/
static inline size_t wpabuf_size(const struct wpabuf *buf)
{
return buf->size;
}
/**
* wpabuf_len - Get the current length of a wpabuf buffer data
* @buf: wpabuf buffer
* Returns: Currently used length of the buffer
*/
static inline size_t wpabuf_len(const struct wpabuf *buf)
{
return buf->used;
}
/**
* wpabuf_tailroom - Get size of available tail room in the end of the buffer
* @buf: wpabuf buffer
* Returns: Tail room (in bytes) of available space in the end of the buffer
*/
static inline size_t wpabuf_tailroom(const struct wpabuf *buf)
{
return buf->size - buf->used;
}
/**
* wpabuf_head - Get pointer to the head of the buffer data
* @buf: wpabuf buffer
* Returns: Pointer to the head of the buffer data
*/
static inline const void *wpabuf_head(const struct wpabuf *buf)
{
return buf->buf;
}
static inline const u8 *wpabuf_head_u8(const struct wpabuf *buf)
{
return wpabuf_head(buf);
}
/**
* wpabuf_mhead - Get modifiable pointer to the head of the buffer data
* @buf: wpabuf buffer
* Returns: Pointer to the head of the buffer data
*/
static inline void *wpabuf_mhead(struct wpabuf *buf)
{
return buf->buf;
}
static inline u8 *wpabuf_mhead_u8(struct wpabuf *buf)
{
return wpabuf_mhead(buf);
}
static inline void wpabuf_put_u8(struct wpabuf *buf, u8 data)
{
u8 *pos = NULL;
if ( buf == NULL)
return;
pos = wpabuf_put(buf, 1);
*pos = data;
}
static inline void wpabuf_put_le16(struct wpabuf *buf, u16 data)
{
u8 *pos = NULL;
if ( buf == NULL)
return;
pos = wpabuf_put(buf, 2);
WPA_PUT_LE16(pos, data);
}
static inline void wpabuf_put_le32(struct wpabuf *buf, u32 data)
{
u8 *pos = NULL;
if ( buf == NULL)
return;
pos = wpabuf_put(buf, 4);
WPA_PUT_LE32(pos, data);
}
static inline void wpabuf_put_be16(struct wpabuf *buf, u16 data)
{
u8 *pos = NULL;
if ( buf == NULL)
return;
pos = wpabuf_put(buf, 2);
WPA_PUT_BE16(pos, data);
}
static inline void wpabuf_put_be24(struct wpabuf *buf, u32 data)
{
u8 *pos = NULL;
if ( buf == NULL)
return;
pos = wpabuf_put(buf, 3);
WPA_PUT_BE24(pos, data);
}
static inline void wpabuf_put_be32(struct wpabuf *buf, u32 data)
{
u8 *pos = NULL;
if ( buf == NULL)
return;
pos = wpabuf_put(buf, 4);
WPA_PUT_BE32(pos, data);
}
// encr >> 16 B 64 - 16 = 48
static inline void wpabuf_put_data(struct wpabuf *buf, const void *data, size_t len)
{
if ( buf == NULL)
return;
if (data)
os_memcpy(wpabuf_put(buf, len), data, len);
}
static inline void wpabuf_put_buf(struct wpabuf *dst,
const struct wpabuf *src)
{
if ( dst == NULL)
return;
wpabuf_put_data(dst, wpabuf_head(src), wpabuf_len(src));
}
static inline void wpabuf_set(struct wpabuf *buf, const void *data, size_t len)
{
if ( buf == NULL)
return;
buf->buf = (u8 *) data;
buf->flags = WPABUF_FLAG_EXT_DATA;
buf->size = buf->used = len;
}
static inline void wpabuf_put_str(struct wpabuf *dst, const char *str)
{
if ( dst == NULL)
return;
wpabuf_put_data(dst, str, os_strlen(str));
}
#endif /* WPABUF_H */

View File

@@ -0,0 +1,324 @@
/*
* Wi-Fi Protected Setup - message definitions
* Copyright (c) 2008, Jouni Malinen <j@w1.fi>
*
* This software may be distributed under the terms of the BSD license.
* See README for more details.
*/
#ifndef WPS_DEFS_H
#define WPS_DEFS_H
#ifdef CONFIG_WPS2
#define WPS_VERSION 0x20
#else /* CONFIG_WPS2 */
#define WPS_VERSION 0x10
#endif /* CONFIG_WPS2 */
/* Diffie-Hellman 1536-bit MODP Group; RFC 3526, Group 5 */
#define WPS_DH_GROUP (5)
#define WPS_UUID_LEN (16)
#define WPS_NONCE_LEN (16)
#define WPS_AUTHENTICATOR_LEN (8)
#define WPS_AUTHKEY_LEN (32)
#define WPS_KEYWRAPKEY_LEN (16)
#define WPS_EMSK_LEN (32)
#define WPS_PSK_LEN (16)
#define WPS_SECRET_NONCE_LEN (16)
#define WPS_HASH_LEN (32)
#define WPS_KWA_LEN (8)
#define WPS_MGMTAUTHKEY_LEN (32)
#define WPS_MGMTENCKEY_LEN (16)
#define WPS_MGMT_KEY_ID_LEN (16)
#define WPS_OOB_DEVICE_PASSWORD_MIN_LEN (16)
#define WPS_OOB_DEVICE_PASSWORD_LEN (32)
#define WPS_OOB_PUBKEY_HASH_LEN (20)
/* Attribute Types */
enum wps_attribute {
ATTR_AP_CHANNEL = 0x1001,
ATTR_ASSOC_STATE = 0x1002,
ATTR_AUTH_TYPE = 0x1003,
ATTR_AUTH_TYPE_FLAGS = 0x1004,
ATTR_AUTHENTICATOR = 0x1005,
ATTR_CONFIG_METHODS = 0x1008,
ATTR_CONFIG_ERROR = 0x1009,
ATTR_CONFIRM_URL4 = 0x100a,
ATTR_CONFIRM_URL6 = 0x100b,
ATTR_CONN_TYPE = 0x100c,
ATTR_CONN_TYPE_FLAGS = 0x100d,
ATTR_CRED = 0x100e,
ATTR_ENCR_TYPE = 0x100f,
ATTR_ENCR_TYPE_FLAGS = 0x1010,
ATTR_DEV_NAME = 0x1011,
ATTR_DEV_PASSWORD_ID = 0x1012,
ATTR_E_HASH1 = 0x1014,
ATTR_E_HASH2 = 0x1015,
ATTR_E_SNONCE1 = 0x1016,
ATTR_E_SNONCE2 = 0x1017,
ATTR_ENCR_SETTINGS = 0x1018,
ATTR_ENROLLEE_NONCE = 0x101a,
ATTR_FEATURE_ID = 0x101b,
ATTR_IDENTITY = 0x101c,
ATTR_IDENTITY_PROOF = 0x101d,
ATTR_KEY_WRAP_AUTH = 0x101e,
ATTR_KEY_ID = 0x101f,
ATTR_MAC_ADDR = 0x1020,
ATTR_MANUFACTURER = 0x1021,
ATTR_MSG_TYPE = 0x1022,
ATTR_MODEL_NAME = 0x1023,
ATTR_MODEL_NUMBER = 0x1024,
ATTR_NETWORK_INDEX = 0x1026,
ATTR_NETWORK_KEY = 0x1027,
ATTR_NETWORK_KEY_INDEX = 0x1028,
ATTR_NEW_DEVICE_NAME = 0x1029,
ATTR_NEW_PASSWORD = 0x102a,
ATTR_OOB_DEVICE_PASSWORD = 0x102c,
ATTR_OS_VERSION = 0x102d,
ATTR_POWER_LEVEL = 0x102f,
ATTR_PSK_CURRENT = 0x1030,
ATTR_PSK_MAX = 0x1031,
ATTR_PUBLIC_KEY = 0x1032,
ATTR_RADIO_ENABLE = 0x1033,
ATTR_REBOOT = 0x1034,
ATTR_REGISTRAR_CURRENT = 0x1035,
ATTR_REGISTRAR_ESTABLISHED = 0x1036,
ATTR_REGISTRAR_LIST = 0x1037,
ATTR_REGISTRAR_MAX = 0x1038,
ATTR_REGISTRAR_NONCE = 0x1039,
ATTR_REQUEST_TYPE = 0x103a,
ATTR_RESPONSE_TYPE = 0x103b,
ATTR_RF_BANDS = 0x103c,
ATTR_R_HASH1 = 0x103d,
ATTR_R_HASH2 = 0x103e,
ATTR_R_SNONCE1 = 0x103f,
ATTR_R_SNONCE2 = 0x1040,
ATTR_SELECTED_REGISTRAR = 0x1041,
ATTR_SERIAL_NUMBER = 0x1042,
ATTR_WPS_STATE = 0x1044,
ATTR_SSID = 0x1045,
ATTR_TOTAL_NETWORKS = 0x1046,
ATTR_UUID_E = 0x1047,
ATTR_UUID_R = 0x1048,
ATTR_VENDOR_EXT = 0x1049,
ATTR_VERSION = 0x104a,
ATTR_X509_CERT_REQ = 0x104b,
ATTR_X509_CERT = 0x104c,
ATTR_EAP_IDENTITY = 0x104d,
ATTR_MSG_COUNTER = 0x104e,
ATTR_PUBKEY_HASH = 0x104f,
ATTR_REKEY_KEY = 0x1050,
ATTR_KEY_LIFETIME = 0x1051,
ATTR_PERMITTED_CFG_METHODS = 0x1052,
ATTR_SELECTED_REGISTRAR_CONFIG_METHODS = 0x1053,
ATTR_PRIMARY_DEV_TYPE = 0x1054,
ATTR_SECONDARY_DEV_TYPE_LIST = 0x1055,
ATTR_PORTABLE_DEV = 0x1056,
ATTR_AP_SETUP_LOCKED = 0x1057,
ATTR_APPLICATION_EXT = 0x1058,
ATTR_EAP_TYPE = 0x1059,
ATTR_IV = 0x1060,
ATTR_KEY_PROVIDED_AUTO = 0x1061,
ATTR_802_1X_ENABLED = 0x1062,
ATTR_APPSESSIONKEY = 0x1063,
ATTR_WEPTRANSMITKEY = 0x1064,
ATTR_REQUESTED_DEV_TYPE = 0x106a,
ATTR_EXTENSIBILITY_TEST = 0x10fa /* _NOT_ defined in the spec */
};
#define WPS_VENDOR_ID_WFA 14122
/* WFA Vendor Extension subelements */
enum {
WFA_ELEM_VERSION2 = 0x00,
WFA_ELEM_AUTHORIZEDMACS = 0x01,
WFA_ELEM_NETWORK_KEY_SHAREABLE = 0x02,
WFA_ELEM_REQUEST_TO_ENROLL = 0x03,
WFA_ELEM_SETTINGS_DELAY_TIME = 0x04
};
/* Device Password ID */
enum wps_dev_password_id {
DEV_PW_DEFAULT = 0x0000,
DEV_PW_USER_SPECIFIED = 0x0001,
DEV_PW_MACHINE_SPECIFIED = 0x0002,
DEV_PW_REKEY = 0x0003,
DEV_PW_PUSHBUTTON = 0x0004,
DEV_PW_REGISTRAR_SPECIFIED = 0x0005
};
/* Message Type */
enum wps_msg_type {
WPS_START = 0x00,
WPS_Beacon = 0x01,
WPS_ProbeRequest = 0x02,
WPS_ProbeResponse = 0x03,
WPS_M1 = 0x04,
WPS_M2 = 0x05,
WPS_M2D = 0x06,
WPS_M3 = 0x07,
WPS_M4 = 0x08,
WPS_M5 = 0x09,
WPS_M6 = 0x0a,
WPS_M7 = 0x0b,
WPS_M8 = 0x0c,
WPS_WSC_ACK = 0x0d,
WPS_WSC_NACK = 0x0e,
WPS_WSC_DONE = 0x0f
};
/* Authentication Type Flags */
#define WPS_AUTH_OPEN 0x0001
#define WPS_AUTH_WPAPSK 0x0002
#define WPS_AUTH_SHARED 0x0004
#define WPS_AUTH_WPA 0x0008
#define WPS_AUTH_WPA2 0x0010
#define WPS_AUTH_WPA2PSK 0x0020
#define WPS_AUTH_TYPES (WPS_AUTH_OPEN | WPS_AUTH_WPAPSK | WPS_AUTH_SHARED | \
WPS_AUTH_WPA | WPS_AUTH_WPA2 | WPS_AUTH_WPA2PSK)
/* Encryption Type Flags */
#define WPS_ENCR_NONE 0x0001
#define WPS_ENCR_WEP 0x0002
#define WPS_ENCR_TKIP 0x0004
#define WPS_ENCR_AES 0x0008
#define WPS_ENCR_TYPES (WPS_ENCR_NONE | WPS_ENCR_WEP | WPS_ENCR_TKIP | \
WPS_ENCR_AES)
/* Configuration Error */
enum wps_config_error {
WPS_CFG_NO_ERROR = 0,
WPS_CFG_OOB_IFACE_READ_ERROR = 1,
WPS_CFG_DECRYPTION_CRC_FAILURE = 2,
WPS_CFG_24_CHAN_NOT_SUPPORTED = 3,
WPS_CFG_50_CHAN_NOT_SUPPORTED = 4,
WPS_CFG_SIGNAL_TOO_WEAK = 5,
WPS_CFG_NETWORK_AUTH_FAILURE = 6,
WPS_CFG_NETWORK_ASSOC_FAILURE = 7,
WPS_CFG_NO_DHCP_RESPONSE = 8,
WPS_CFG_FAILED_DHCP_CONFIG = 9,
WPS_CFG_IP_ADDR_CONFLICT = 10,
WPS_CFG_NO_CONN_TO_REGISTRAR = 11,
WPS_CFG_MULTIPLE_PBC_DETECTED = 12,
WPS_CFG_ROGUE_SUSPECTED = 13,
WPS_CFG_DEVICE_BUSY = 14,
WPS_CFG_SETUP_LOCKED = 15,
WPS_CFG_MSG_TIMEOUT = 16,
WPS_CFG_REG_SESS_TIMEOUT = 17,
WPS_CFG_DEV_PASSWORD_AUTH_FAILURE = 18
};
/* RF Bands */
#define WPS_RF_24GHZ (0x01)
#define WPS_RF_50GHZ (0x02)
/* Config Methods */
#define WPS_CONFIG_USBA (0x0001)
#define WPS_CONFIG_ETHERNET (0x0002)
#define WPS_CONFIG_LABEL (0x0004)
#define WPS_CONFIG_DISPLAY (0x0008)
#define WPS_CONFIG_EXT_NFC_TOKEN (0x0010)
#define WPS_CONFIG_INT_NFC_TOKEN (0x0020)
#define WPS_CONFIG_NFC_INTERFACE (0x0040)
#define WPS_CONFIG_PUSHBUTTON (0x0080)
#define WPS_CONFIG_KEYPAD (0x0100)
#ifdef CONFIG_WPS2
#define WPS_CONFIG_VIRT_PUSHBUTTON (0x0280)
#define WPS_CONFIG_PHY_PUSHBUTTON (0x0480)
#define WPS_CONFIG_VIRT_DISPLAY (0x2008)
#define WPS_CONFIG_PHY_DISPLAY (0x4008)
#endif /* CONFIG_WPS2 */
/* Connection Type Flags */
#define WPS_CONN_ESS (0x01)
#define WPS_CONN_IBSS (0x02)
/* Wi-Fi Protected Setup State */
enum wps_state {
WPS_STATE_NOT_CONFIGURED = 1,
WPS_STATE_CONFIGURED = 2
};
/* Association State */
enum wps_assoc_state {
WPS_ASSOC_NOT_ASSOC = 0,
WPS_ASSOC_CONN_SUCCESS = 1,
WPS_ASSOC_CFG_FAILURE = 2,
WPS_ASSOC_FAILURE = 3,
WPS_ASSOC_IP_FAILURE = 4
};
#define WPS_DEV_OUI_WFA (0x0050f204)
enum wps_dev_categ {
WPS_DEV_COMPUTER = 1,
WPS_DEV_INPUT = 2,
WPS_DEV_PRINTER = 3,
WPS_DEV_CAMERA = 4,
WPS_DEV_STORAGE = 5,
WPS_DEV_NETWORK_INFRA = 6,
WPS_DEV_DISPLAY = 7,
WPS_DEV_MULTIMEDIA = 8,
WPS_DEV_GAMING = 9,
WPS_DEV_PHONE = 10
};
enum wps_dev_subcateg {
WPS_DEV_COMPUTER_PC = 1,
WPS_DEV_COMPUTER_SERVER = 2,
WPS_DEV_COMPUTER_MEDIA_CENTER = 3,
WPS_DEV_PRINTER_PRINTER = 1,
WPS_DEV_PRINTER_SCANNER = 2,
WPS_DEV_CAMERA_DIGITAL_STILL_CAMERA = 1,
WPS_DEV_STORAGE_NAS = 1,
WPS_DEV_NETWORK_INFRA_AP = 1,
WPS_DEV_NETWORK_INFRA_ROUTER = 2,
WPS_DEV_NETWORK_INFRA_SWITCH = 3,
WPS_DEV_DISPLAY_TV = 1,
WPS_DEV_DISPLAY_PICTURE_FRAME = 2,
WPS_DEV_DISPLAY_PROJECTOR = 3,
WPS_DEV_MULTIMEDIA_DAR = 1,
WPS_DEV_MULTIMEDIA_PVR = 2,
WPS_DEV_MULTIMEDIA_MCX = 3,
WPS_DEV_GAMING_XBOX = 1,
WPS_DEV_GAMING_XBOX360 = 2,
WPS_DEV_GAMING_PLAYSTATION = 3,
WPS_DEV_PHONE_WINDOWS_MOBILE = 1
};
/* Request Type */
enum wps_request_type {
WPS_REQ_ENROLLEE_INFO = 0,
WPS_REQ_ENROLLEE = 1,
WPS_REQ_REGISTRAR = 2,
WPS_REQ_WLAN_MANAGER_REGISTRAR = 3
};
/* Response Type */
enum wps_response_type {
WPS_RESP_ENROLLEE_INFO = 0,
WPS_RESP_ENROLLEE = 1,
WPS_RESP_REGISTRAR = 2,
WPS_RESP_AP = 3
};
/* Walk Time for push button configuration (in seconds) */
#define WPS_PBC_WALK_TIME (120)
#define WPS_MAX_AUTHORIZED_MACS (5)
#endif /* WPS_DEFS_H */

View File

@@ -0,0 +1,610 @@
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include "FreeRTOS.h"
#include "task.h"
#include "main.h"
#include "queue.h"
#include "utils/os.h"
#include <lwip_netconf.h>
#include <lwip/netif.h>
#include "wifi/wifi_conf.h"
#include <platform/platform_stdlib.h>
#define WLAN0_NAME "wlan0"
#ifndef ENABLE
#define ENABLE (1)
#endif
#ifndef DISABLE
#define DISABLE (0)
#endif
u8 eap_phase = 0;
u8 eap_method = 0;
// eap config arguments
char *eap_target_ssid = NULL;
char *eap_identity = NULL;
char *eap_password = NULL;
// if set eap_ca_cert and defined(EAP_SSL_VERIFY_SERVER), client will verify server's cert
const unsigned char *eap_ca_cert = NULL;
// if set eap_client_cert, eap_client_key, and defined(EAP_SSL_VERIFY_CLIENT), client will send its cert to server
const unsigned char *eap_client_cert = NULL;
const unsigned char *eap_client_key = NULL;
char *eap_client_key_pwd = NULL;
void eap_eapol_recvd_hdl(char *buf, int buf_len, int flags, void* handler_user_data);
void eap_eapol_start_hdl(char *buf, int buf_len, int flags, void* handler_user_data);
static int connect_by_open_system(char *target_ssid);
void set_eap_phase(unsigned char is_trigger_eap){
eap_phase = is_trigger_eap;
}
int get_eap_phase(void){
return eap_phase;
}
int get_eap_method(void){
return eap_method;
}
void reset_config(void){
eap_target_ssid = NULL;
eap_identity = NULL;
eap_password = NULL;
eap_ca_cert = NULL;
eap_client_cert = NULL;
eap_client_key = NULL;
eap_client_key_pwd = NULL;
}
void judge_station_disconnect(void)
{
int mode = 0;
unsigned char ssid[33];
wext_get_mode(WLAN0_NAME, &mode);
switch(mode) {
case IW_MODE_MASTER: //In AP mode
wifi_off();
vTaskDelay(20);
wifi_on(RTW_MODE_STA);
break;
case IW_MODE_INFRA: //In STA mode
if(wext_get_ssid(WLAN0_NAME, ssid) > 0)
wifi_disconnect();
}
}
void eap_disconnected_hdl(char *buf, int buf_len, int flags, void* handler_user_data){
// printf("disconnected\n");
wifi_unreg_event_handler(WIFI_EVENT_EAPOL_RECVD, eap_eapol_recvd_hdl);
wifi_unreg_event_handler(WIFI_EVENT_DISCONNECT, eap_disconnected_hdl);
eap_peer_unregister_methods();
eap_sm_deinit();
//reset_config();
}
/*
void eap_config(void){
eap_target_ssid = "Test_eap";
eap_identity = "guest2";
eap_password = "test2";
eap_client_cert = \
"-----BEGIN CERTIFICATE-----\r\n" \
"MIIC9zCCAd8CAQMwDQYJKoZIhvcNAQEEBQAwgZMxCzAJBgNVBAYTAkZSMQ8wDQYD\r\n" \
"VQQIEwZSYWRpdXMxEjAQBgNVBAcTCVNvbWV3aGVyZTEVMBMGA1UEChMMRXhhbXBs\r\n" \
"ZSBJbmMuMSAwHgYJKoZIhvcNAQkBFhFhZG1pbkBleGFtcGxlLmNvbTEmMCQGA1UE\r\n" \
"AxMdRXhhbXBsZSBDZXJ0aWZpY2F0ZSBBdXRob3JpdHkwHhcNMTYwMzE1MDgwNzEx\r\n" \
"WhcNMTcwMzE1MDgwNzExWjBzMQswCQYDVQQGEwJGUjEPMA0GA1UECBMGUmFkaXVz\r\n" \
"MRUwEwYDVQQKEwxFeGFtcGxlIEluYy4xGjAYBgNVBAMUEXVzZXIyQGV4YW1wbGUu\r\n" \
"Y29tMSAwHgYJKoZIhvcNAQkBFhF1c2VyMkBleGFtcGxlLmNvbTCBnzANBgkqhkiG\r\n" \
"9w0BAQEFAAOBjQAwgYkCgYEAqESlV4OYfBcIgZ+Cs8mWpiBjhvKoa0/kIe7saqhC\r\n" \
"e5q4snox0jdkUpLcc4vOs3vQ7ZGnimqTltA9oF6XNUzTWW4vlJTKEfrCWK085l7c\r\n" \
"DHFvHavH3E6vuP71lI7jq4PLXbo2TvZK+uBul4ozjzVWihaZBtz8eLHq446h/D/p\r\n" \
"kzkCAwEAATANBgkqhkiG9w0BAQQFAAOCAQEAAfhVAIkNdeeUNJud720uUHVnIcxz\r\n" \
"GXWI+Svi1qchuTEnRNhLwXmnE+A0WWSHyfdR6FvzdT3xtz3K50iOif8jY2gCGkSK\r\n" \
"8RjKr97228SwbrGO9y9+dYIjH1uz9cBpoVKcpzdsWpKObrDPDYyReHSWo99jM2+O\r\n" \
"vfJxnBw4PLiBj7Q0/dpd6o4JXyp7Cxa0mB4/+cZqjCzzuKfuK3WP7j6laMCV6mg4\r\n" \
"wRZ528IdwDqB7OOqsDm1PVQM8vzny9PM6ikWUCRTVNQJN8RDLkrHR3FRjy15YLdt\r\n" \
"yOfDqVnT/z0wGBaxnNziSJjqPGHPpRi4bJFGXwXOhtknKmciKzfj9/npoQ==\r\n" \
"-----END CERTIFICATE-----\r\n";
eap_client_key = \
"-----BEGIN RSA PRIVATE KEY-----\r\n" \
"MIICXQIBAAKBgQCoRKVXg5h8FwiBn4KzyZamIGOG8qhrT+Qh7uxqqEJ7mriyejHS\r\n" \
"N2RSktxzi86ze9DtkaeKapOW0D2gXpc1TNNZbi+UlMoR+sJYrTzmXtwMcW8dq8fc\r\n" \
"Tq+4/vWUjuOrg8tdujZO9kr64G6XijOPNVaKFpkG3Px4serjjqH8P+mTOQIDAQAB\r\n" \
"AoGARI+LyweshssfxSkIKVc3EcNaqi6PHwJzUrw2ChM624AkR1xwllXJg7ehKVdK\r\n" \
"xmjprRLO8CASuL1qjsBb3fTKnBl+sIVxIFS0AI4Y3ri8VUKbangvSsI7pCzAFry7\r\n" \
"p1gmy9WWRV2ZEa+dV8xcrjb3bloT7hcdeLehgBCvExJIQM0CQQDXlSAKdW3AhYyj\r\n" \
"1A+pfyBSGxJbpSwNyyWgwHIHHjxendxmdUbrc8EbAu1eNKbP58TLgdCZsKcMonAv\r\n" \
"MY1Y2/nnAkEAx9CrUaCU8pJqXTRypM5JtexLKnYMJhpnA9uUILBQOq4Oe0eruyF5\r\n" \
"SaSxhyJYXY491ahWYPF0PTb3jkUhoN+l3wJBAJZthjgGDJlEFwjSFkOtYz4nib3N\r\n" \
"GVpeoFj1MBvrazCScpJDz0LIOLzCZCNSFfwIu3dNk+NKMqZMSn+D0h9pD40CQQC5\r\n" \
"K9n4NXaTLbjAU2CC9mE85JPr76XmkcUxwAWQHZTcLH1jJdIyAx1hb+zNLLjzSmRn\r\n" \
"Yi9ae6ibKhtUjyBQ87HFAkA2Bb3z7NUx+AA2g2HZocFZFShBxylACyQkl8FAFZtf\r\n" \
"osudmKdFQHyAWuBMex4tpz/OLTqJ1ecL1JQeC7OvlpEX\r\n" \
"-----END RSA PRIVATE KEY-----\r\n";
eap_ca_cert = \
"-----BEGIN CERTIFICATE-----\r\n" \
"MIIEpzCCA4+gAwIBAgIJAPvZaozpdfjkMA0GCSqGSIb3DQEBCwUAMIGTMQswCQYD\r\n" \
"VQQGEwJGUjEPMA0GA1UECBMGUmFkaXVzMRIwEAYDVQQHEwlTb21ld2hlcmUxFTAT\r\n" \
"BgNVBAoTDEV4YW1wbGUgSW5jLjEgMB4GCSqGSIb3DQEJARYRYWRtaW5AZXhhbXBs\r\n" \
"ZS5jb20xJjAkBgNVBAMTHUV4YW1wbGUgQ2VydGlmaWNhdGUgQXV0aG9yaXR5MB4X\r\n" \
"DTE2MDMxNDExMjU0OVoXDTE2MDQxMzExMjU0OVowgZMxCzAJBgNVBAYTAkZSMQ8w\r\n" \
"DQYDVQQIEwZSYWRpdXMxEjAQBgNVBAcTCVNvbWV3aGVyZTEVMBMGA1UEChMMRXhh\r\n" \
"bXBsZSBJbmMuMSAwHgYJKoZIhvcNAQkBFhFhZG1pbkBleGFtcGxlLmNvbTEmMCQG\r\n" \
"A1UEAxMdRXhhbXBsZSBDZXJ0aWZpY2F0ZSBBdXRob3JpdHkwggEiMA0GCSqGSIb3\r\n" \
"DQEBAQUAA4IBDwAwggEKAoIBAQC9pireu0aCDLNfMaGv3vId7RXjUhQwSK0jV2Oc\r\n" \
"SyvlKWH3P/N+5kLrP2iL6SCzyETVDXZ0vOsAMjcBF0zHp16prXV0d51cTUqeWBb0\r\n" \
"I5UnGxleIuuOfSg8zLUJoBWZPqLv++eZ5WgOKHt7SXocjvg7TU5t/TMB0Y8OCz3H\r\n" \
"CW2vJ/XKMgMA9HDUu4g57cJu88i1JPRpyFaz/HIQBc7+UNb9z+q09uTZKWTmEMqi\r\n" \
"E2U0EEIs7EtbxnOze1/8C4XNlmztrEdwvu6UEBU/TFkUoh9M646NkkBK7wP9n9pv\r\n" \
"T0nPQRJiiCrICzVqUtlEi9lIKpbBSMbQ0KzrGF7lGTgm4rz9AgMBAAGjgfswgfgw\r\n" \
"HQYDVR0OBBYEFIVyecka74kvOKIW0BjlTc/B+a2NMIHIBgNVHSMEgcAwgb2AFIVy\r\n" \
"ecka74kvOKIW0BjlTc/B+a2NoYGZpIGWMIGTMQswCQYDVQQGEwJGUjEPMA0GA1UE\r\n" \
"CBMGUmFkaXVzMRIwEAYDVQQHEwlTb21ld2hlcmUxFTATBgNVBAoTDEV4YW1wbGUg\r\n" \
"SW5jLjEgMB4GCSqGSIb3DQEJARYRYWRtaW5AZXhhbXBsZS5jb20xJjAkBgNVBAMT\r\n" \
"HUV4YW1wbGUgQ2VydGlmaWNhdGUgQXV0aG9yaXR5ggkA+9lqjOl1+OQwDAYDVR0T\r\n" \
"BAUwAwEB/zANBgkqhkiG9w0BAQsFAAOCAQEAZYHM26sxbKOckVqJJ1QY0U2QFlGP\r\n" \
"1GYd8v27znxdnRmSonDvv3GjFfhwoyDk0JUuxkK/33ikCxihrgoO/EQTY9BV2OpW\r\n" \
"qkB1PDtb3i5ZRNvfjmW0pVA4p+GmdTGaEE5pTlcVnorzVrUeFKaZakb+IDFYzmeF\r\n" \
"xp8B3Bb5wvinDligLOaJnSlgS8QeeIab9HZfaVTTuPmVK6zE6D54Y0dJPnykvDdE\r\n" \
"cGN0FC+migfilFjJgkDJ0r78nwes55L8zjoofiZuO03rrHww6ARc3v1jYzAufddk\r\n" \
"QTiZHgjlMQb2XXMmXLn8kBgoDnqkXFNe8j0h8uxIJSrjOoIyn1h1wvX5/w==\r\n" \
"-----END CERTIFICATE-----\r\n";
}
*/
int eap_start(char *method){
#ifdef CONFIG_ENABLE_EAP
int ret = -1;
//unsigned long tick1 = xTaskGetTickCount();
//unsigned long tick2;
if(rltk_wlan_running(WLAN1_IDX)){
printf("\n\rNot support con-current mode!\n\r");
return -1;
}
judge_station_disconnect();
#if CONFIG_ENABLE_PEAP
if(strcmp(method,"peap") == 0){
ret = set_eap_peap_method();
}
#endif
#if CONFIG_ENABLE_TLS
if(strcmp(method,"tls") == 0){
ret = set_eap_tls_method();
}
#endif
#if CONFIG_ENABLE_TTLS
if(strcmp(method,"ttls") == 0){
ret = set_eap_ttls_method();
}
#endif
if(ret == -1){
printf("\r\neap method %s not supported\r\n", method);
return -1;
}
eap_method = get_eap_ctx_method();
printf("\n==================== %s_start ====================\n", method);
//eap_config();
set_eap_phase(ENABLE);
wifi_reg_event_handler(WIFI_EVENT_EAPOL_START, eap_eapol_start_hdl, NULL);
wifi_reg_event_handler(WIFI_EVENT_EAPOL_RECVD, eap_eapol_recvd_hdl, NULL);
ret = connect_by_open_system(eap_target_ssid);
#if CONFIG_LWIP_LAYER
/* Start DHCPClient */
if(ret == 0)
LwIP_DHCP(0, DHCP_START);
#endif
wifi_unreg_event_handler(WIFI_EVENT_EAPOL_START, eap_eapol_start_hdl);
// for re-authentication when session timeout
wifi_reg_event_handler(WIFI_EVENT_DISCONNECT, eap_disconnected_hdl, NULL);
//wifi_unreg_event_handler(WIFI_EVENT_EAPOL_RECVD, eap_eapol_recvd_hdl);
set_eap_phase(DISABLE);
// eap failed, disconnect
if(ret != 0){
judge_station_disconnect();
eap_disconnected_hdl(NULL, 0, 0, NULL);
rtw_msleep_os(200); //wait handler done
printf("\r\nERROR: connect to AP by %s failed\n", method);
}
eap_sm_deinit();
printf("\n==================== %s_finish ====================\n", method);
//tick2 = xTaskGetTickCount();
//printf("\r\nConnected after %dms.\n", (tick2-tick1));
return ret;
#else
return -1;
#endif
}
static int connect_by_open_system(char *target_ssid)
{
int retry_count = 0, ret;
if (target_ssid != NULL) {
while (1) {
rtw_msleep_os(500); //wait scan complete.
ret = wifi_connect(target_ssid,
RTW_SECURITY_OPEN,
NULL,
strlen(target_ssid),
0,
0,
NULL);
if (ret == RTW_SUCCESS) {
//printf("\r\n[EAP]Associate with AP success\n");
break;
}
if (retry_count == 0) {
//printf("\r\n[EAP]Associate with AP failed %d\n", ret);
return -1;
}
retry_count --;
printf("Retry connection...\n");
judge_station_disconnect();
set_eap_phase(ENABLE);
}
} else {
printf("\r\n[EAP]Target SSID is NULL\n");
return -1;
}
return 0;
}
static void eap_autoreconnect_thread(void *method)
{
eap_start((char*)method);
vTaskDelete(NULL);
}
void eap_autoreconnect_hdl(u8 method_id){
#ifdef CONFIG_ENABLE_EAP
char *method;
switch(method_id){
case 25: // EAP_TYPE_PEAP
method = "peap";
break;
case 13: // EAP_TYPE_TLS
method = "tls";
break;
case 21: // EAP_TYPE_TTLS
method = "ttls";
break;
default:
printf("invalid eap method\n");
return;
}
if(xTaskCreate(eap_autoreconnect_thread, ((const char*)"eap_autoreconnect_thread"), 1024, (void*) method, tskIDLE_PRIORITY + 1, NULL) != pdPASS)
printf("\n\r%s xTaskCreate failed\n", __FUNCTION__);
#endif
}
// copy from ssl_client_ext.c
#if CONFIG_USE_POLARSSL
#include <polarssl/ssl.h>
#include <polarssl/memory.h>
int max_buf_bio_size = SSL_BUFFER_LEN;
#if ENABLE_EAP_SSL_VERIFY_CLIENT
static x509_crt* _cli_crt = NULL;
static pk_context* _clikey_rsa = NULL;
#endif
#if ENABLE_EAP_SSL_VERIFY_SERVER
static x509_crt* _ca_crt = NULL;
static int eap_verify(void *data, x509_crt *crt, int depth, int *flags)
{
//char buf[1024];
((void) data);
printf("\nVerify requested for (Depth %d):\n", depth);
//x509_crt_info(buf, sizeof(buf) - 1, "", crt);
//printf("%s", buf);
if(((*flags) & BADCERT_EXPIRED) != 0)
printf("server certificate has expired\n");
if(((*flags) & BADCERT_REVOKED) != 0)
printf(" ! server certificate has been revoked\n");
if(((*flags) & BADCERT_CN_MISMATCH) != 0)
printf(" ! CN mismatch\n");
if(((*flags) & BADCERT_NOT_TRUSTED) != 0)
printf(" ! self-signed or not signed by a trusted CA\n");
if(((*flags) & BADCRL_NOT_TRUSTED) != 0)
printf(" ! CRL not trusted\n");
if(((*flags) & BADCRL_EXPIRED) != 0)
printf(" ! CRL expired\n");
if(((*flags) & BADCERT_OTHER) != 0)
printf(" ! other (unknown) flag\n");
if((*flags) == 0)
printf(" Certificate verified without error flags\n");
return(0);
}
#endif
int eap_cert_init(void)
{
#if ENABLE_EAP_SSL_VERIFY_CLIENT
if(eap_client_cert != NULL && eap_client_key != NULL){
_cli_crt = polarssl_malloc(sizeof(x509_crt));
if(_cli_crt)
x509_crt_init(_cli_crt);
else
return -1;
_clikey_rsa = polarssl_malloc(sizeof(pk_context));
if(_clikey_rsa)
pk_init(_clikey_rsa);
else
return -1;
}
#endif
#if ENABLE_EAP_SSL_VERIFY_SERVER
if(eap_ca_cert != NULL){
_ca_crt = polarssl_malloc(sizeof(x509_crt));
if(_ca_crt)
x509_crt_init(_ca_crt);
else
return -1;
}
#endif
return 0;
}
void eap_client_cert_free(void)
{
#if ENABLE_EAP_SSL_VERIFY_CLIENT
if(eap_client_cert != NULL && eap_client_key != NULL){
if(_cli_crt) {
x509_crt_free(_cli_crt);
polarssl_free(_cli_crt);
_cli_crt = NULL;
}
if(_clikey_rsa) {
pk_free(_clikey_rsa);
polarssl_free(_clikey_rsa);
_clikey_rsa = NULL;
}
}
#endif
}
void eap_server_cert_free(void)
{
#if ENABLE_EAP_SSL_VERIFY_SERVER
if(eap_ca_cert != NULL){
if(_ca_crt) {
x509_crt_free(_ca_crt);
polarssl_free(_ca_crt);
_ca_crt = NULL;
}
}
#endif
}
int eap_cert_setup(ssl_context *ssl)
{
#if ENABLE_EAP_SSL_VERIFY_CLIENT
if(eap_client_cert != NULL && eap_client_key != NULL){
if(x509_crt_parse(_cli_crt, eap_client_cert, strlen(eap_client_cert)) != 0)
return -1;
if(pk_parse_key(_clikey_rsa, eap_client_key, strlen(eap_client_key), eap_client_key_pwd, strlen(eap_client_key_pwd)) != 0)
return -1;
ssl_set_own_cert(ssl, _cli_crt, _clikey_rsa);
}
#endif
#if ENABLE_EAP_SSL_VERIFY_SERVER
if(eap_ca_cert != NULL){
if(x509_crt_parse(_ca_crt, eap_ca_cert, strlen(eap_ca_cert)) != 0)
return -1;
ssl_set_ca_chain(ssl, _ca_crt, NULL, NULL);
ssl_set_authmode(ssl, SSL_VERIFY_REQUIRED);
ssl_set_verify(ssl, eap_verify, NULL);
}
#endif
return 0;
}
#elif CONFIG_USE_MBEDTLS
#include <mbedtls/config.h>
#include <mbedtls/platform.h>
#include <mbedtls/ssl.h>
#include <mbedtls/ssl_internal.h>
#if CONFIG_EXAMPLE_AMAZON_FREERTOS || CONFIG_EXAMPLE_AMAZON_AFQP_TESTS
int max_buf_bio_size = MBEDTLS_SSL_IN_BUFFER_LEN;
#else
int max_buf_bio_size = MBEDTLS_SSL_BUFFER_LEN;
#endif
struct eap_tls{
void *ssl;
void *conf;
void *fd;
};
#if ENABLE_EAP_SSL_VERIFY_CLIENT
static mbedtls_x509_crt* _cli_crt = NULL;
static mbedtls_pk_context* _clikey_rsa = NULL;
#endif
#if ENABLE_EAP_SSL_VERIFY_SERVER
static mbedtls_x509_crt* _ca_crt = NULL;
static int eap_verify(void *data, mbedtls_x509_crt *crt, int depth, int *flags)
{
//char buf[1024];
((void) data);
printf("\nVerify requested for (Depth %d):\n", depth);
//mbedtls_x509_crt_info(buf, sizeof(buf) - 1, "", crt);
//printf("%s", buf);
if(((*flags) & MBEDTLS_X509_BADCERT_EXPIRED) != 0)
printf("server certificate has expired\n");
if(((*flags) & MBEDTLS_X509_BADCERT_REVOKED) != 0)
printf(" ! server certificate has been revoked\n");
if(((*flags) & MBEDTLS_X509_BADCERT_CN_MISMATCH) != 0)
printf(" ! CN mismatch\n");
if(((*flags) & MBEDTLS_X509_BADCERT_NOT_TRUSTED) != 0)
printf(" ! self-signed or not signed by a trusted CA\n");
if(((*flags) & MBEDTLS_X509_BADCRL_NOT_TRUSTED) != 0)
printf(" ! CRL not trusted\n");
if(((*flags) & MBEDTLS_X509_BADCRL_EXPIRED) != 0)
printf(" ! CRL expired\n");
if(((*flags) & MBEDTLS_X509_BADCERT_OTHER) != 0)
printf(" ! other (unknown) flag\n");
if((*flags) == 0)
printf(" Certificate verified without error flags\n");
return(0);
}
#endif
int eap_cert_init(void)
{
#if ENABLE_EAP_SSL_VERIFY_CLIENT
if(eap_client_cert != NULL && eap_client_key != NULL){
_cli_crt = mbedtls_calloc(1, sizeof(mbedtls_x509_crt));
if(_cli_crt)
mbedtls_x509_crt_init(_cli_crt);
else
return -1;
_clikey_rsa = mbedtls_calloc(1, sizeof(mbedtls_pk_context));
if(_clikey_rsa)
mbedtls_pk_init(_clikey_rsa);
else
return -1;
}
#endif
#if ENABLE_EAP_SSL_VERIFY_SERVER
if(eap_ca_cert != NULL){
_ca_crt = mbedtls_calloc(1, sizeof(mbedtls_x509_crt));
if(_ca_crt)
mbedtls_x509_crt_init(_ca_crt);
else
return -1;
}
#endif
return 0;
}
void eap_client_cert_free(void)
{
#if ENABLE_EAP_SSL_VERIFY_CLIENT
if(eap_client_cert != NULL && eap_client_key != NULL){
if(_cli_crt) {
mbedtls_x509_crt_free(_cli_crt);
mbedtls_free(_cli_crt);
_cli_crt = NULL;
}
if(_clikey_rsa) {
mbedtls_pk_free(_clikey_rsa);
mbedtls_free(_clikey_rsa);
_clikey_rsa = NULL;
}
}
#endif
}
void eap_server_cert_free(void)
{
#if ENABLE_EAP_SSL_VERIFY_SERVER
if(eap_ca_cert != NULL){
if(_ca_crt) {
mbedtls_x509_crt_free(_ca_crt);
mbedtls_free(_ca_crt);
_ca_crt = NULL;
}
}
#endif
}
int eap_cert_setup(struct eap_tls *tls_context)
{
#if ENABLE_EAP_SSL_VERIFY_CLIENT
if(eap_client_cert != NULL && eap_client_key != NULL){
if(mbedtls_x509_crt_parse(_cli_crt, eap_client_cert, strlen(eap_client_cert)+1) != 0)
return -1;
if(mbedtls_pk_parse_key(_clikey_rsa, eap_client_key, strlen(eap_client_key)+1, eap_client_key_pwd, strlen(eap_client_key_pwd)+1) != 0)
return -1;
mbedtls_ssl_conf_own_cert(tls_context->conf, _cli_crt, _clikey_rsa);
}
#endif
#if ENABLE_EAP_SSL_VERIFY_SERVER
if(eap_ca_cert != NULL){
if(mbedtls_x509_crt_parse(_ca_crt, eap_ca_cert, strlen(eap_ca_cert)+1) != 0)
return -1;
mbedtls_ssl_conf_ca_chain(tls_context->conf, _ca_crt, NULL);
mbedtls_ssl_conf_authmode(tls_context->conf, MBEDTLS_SSL_VERIFY_REQUIRED);
mbedtls_ssl_conf_verify(tls_context->conf, eap_verify, NULL);
}
#endif
return 0;
}
#endif /*CONFIG_USE_MBEDTLS*/

View File

@@ -0,0 +1,269 @@
#include "FreeRTOS.h"
#include "task.h"
#include "utils/os.h"
#include <lwip/netif.h>
#include <wifi/wifi_conf.h>
#include "wps/wps_defs.h"
#if CONFIG_ENABLE_P2P
enum p2p_wps_method {
WPS_NOT_READY, WPS_PIN_DISPLAY, WPS_PIN_KEYPAD, WPS_PBC
};
/*NETMASK*/
#define P2P_NETMASK_ADDR0 255
#define P2P_NETMASK_ADDR1 255
#define P2P_NETMASK_ADDR2 255
#define P2P_NETMASK_ADDR3 0
/*Gateway Address*/
#define P2P_GW_ADDR0 192
#define P2P_GW_ADDR1 168
#define P2P_GW_ADDR2 42
#define P2P_GW_ADDR3 1
#define P2P_GO_NEGO_RESULT_SIZE 376//256
xqueue_handle_t queue_for_p2p_nego;
extern void dhcps_init(struct netif * pnetif);
static int hex2num(char c)
{
if (c >= '0' && c <= '9')
return c - '0';
if (c >= 'a' && c <= 'f')
return c - 'a' + 10;
if (c >= 'A' && c <= 'F')
return c - 'A' + 10;
return -1;
}
/**
* hwaddr_aton - Convert ASCII string to MAC address (colon-delimited format)
* @txt: MAC address as a string (e.g., "00:11:22:33:44:55")
* @addr: Buffer for the MAC address (ETH_ALEN = 6 bytes)
* Returns: 0 on success, -1 on failure (e.g., string not a MAC address)
*/
int hwaddr_aton(const char *txt, u8 *addr)
{
int i;
for (i = 0; i < 6; i++) {
int a, b;
a = hex2num(*txt++);
if (a < 0)
return -1;
b = hex2num(*txt++);
if (b < 0)
return -1;
*addr++ = (a << 4) | b;
if (i < 5 && *txt++ != ':')
return -1;
}
return 0;
}
int wifi_start_p2p_go(char *ssid, char *passphrase, u8 channel)
{
extern struct netif xnetif[NET_IF_NUM];
struct netif * pnetif = &xnetif[0];
struct ip_addr ipaddr;
struct ip_addr netmask;
struct ip_addr gw;
IP4_ADDR(&ipaddr, P2P_GW_ADDR0, P2P_GW_ADDR1, P2P_GW_ADDR2, P2P_GW_ADDR3);
IP4_ADDR(&netmask, P2P_NETMASK_ADDR0, P2P_NETMASK_ADDR1 , P2P_NETMASK_ADDR2, P2P_NETMASK_ADDR3);
IP4_ADDR(&gw, P2P_GW_ADDR0, P2P_GW_ADDR1, P2P_GW_ADDR2, P2P_GW_ADDR3);
netif_set_addr(pnetif, &ipaddr, &netmask,&gw);
// start ap
if(wifi_start_ap(ssid,
RTW_SECURITY_WPA2_AES_PSK,
passphrase,
strlen(ssid),
strlen(passphrase),
channel
) != RTW_SUCCESS) {
printf("\n\rERROR: Operation failed!");
return -1;
}
netif_set_default(pnetif);
// start dhcp server
dhcps_init(pnetif);
return 0;
}
void app_callback(char *msg)
{
//From Application
}
void cmd_wifi_p2p_start(int argc, char **argv)
{
extern struct netif xnetif[NET_IF_NUM];
int listen_ch = 1;
int op_ch = 5;
int go_intent = 1;
#if 1
u32 r = 0;
os_get_random((u8 *) &r, sizeof(r));
go_intent = r%15+1; /*1-15*/
os_get_random((u8 *) &r, sizeof(r));
listen_ch = 1 + (r % 3) * 5;
os_get_random((u8 *) &r, sizeof(r));
op_ch = 1 + (r % 3) * 5;
#endif
wifi_off();
os_sleep(0, 20000);
wifi_on(RTW_MODE_P2P);
wifi_p2p_init(xnetif[0].hwaddr, go_intent, listen_ch, op_ch);
}
int cmd_wifi_p2p_auto_go_start(int argc, char **argv)
{
u8 *passphrase = "12345678";
u8 channel = 6; // 1, 6, 11
const char *ssid_in = "DIRECT-34-Ameba";
const char *dev_name = "Ameba1234"; // max strlen 32
const char *manufacturer = "by customer"; // max strlen 64
const char *model_name = "customer"; // max strlen 32
const char *model_number = "v2.0"; // max strlen 32
const char *serial_number = "9"; // max strlen 32
const u8 pri_dev_type[8] = {0x00,0x0A,0x00,0x50,0xF2,0x04,0x00,0x01}; // category ID:0x00,0x0A; sub category ID:0x00,0x01
u8 res[P2P_GO_NEGO_RESULT_SIZE];
u16 config_methods = WPS_CONFIG_DISPLAY | WPS_CONFIG_KEYPAD | WPS_CONFIG_PUSHBUTTON;
if(!is_wifi_p2p_initialized())
return -1;
wifi_p2p_set_dev_name(dev_name);
wifi_p2p_set_manufacturer(manufacturer);
wifi_p2p_set_model_name(model_name);
wifi_p2p_set_model_number(model_number);
wifi_p2p_set_serial_number(serial_number);
wifi_p2p_set_pri_dev_type(pri_dev_type);
wifi_p2p_set_ssid(ssid_in);
wifi_p2p_set_config_methods(config_methods);
wifi_p2p_init_auto_go_params(res, passphrase, channel);
wifi_p2p_start_auto_go(res);
return 0;
}
void cmd_wifi_p2p_stop(int argc, char **argv)
{
wifi_p2p_deinit();
wifi_off();
}
void cmd_p2p_listen(int argc, char **argv)
{
u32 timeout = 0;
if(argc == 2){
timeout = os_atoi((u8*)argv[1]);
printf("\r\n%s(): timeout=%d\n", __func__, timeout);
if(timeout > 3600)
timeout = 3600;
}
wifi_cmd_p2p_listen(timeout);
}
void cmd_p2p_find(int argc, char **argv)
{
wifi_cmd_p2p_find();
}
void cmd_p2p_peers(int argc, char **argv)
{
wifi_cmd_p2p_peers();
}
void cmd_p2p_info(int argc, char **argv)
{
wifi_cmd_p2p_info();
}
void cmd_p2p_disconnect(int argc, char **argv)
{
wifi_cmd_p2p_disconnect();
}
void cmd_p2p_connect(int argc, char **argv)
{
enum p2p_wps_method config_method = WPS_PBC;
char *pin = NULL;
u8 dest[ETH_ALEN] = {0x44, 0x6d, 0x57, 0xd7, 0xce, 0x41};
u8 res[P2P_GO_NEGO_RESULT_SIZE];
int ret = 0, result = 0;
#if 1
if((argc != 2) && (argc != 3) && (argc != 4)) {
printf("\n\rUsage: p2p_connect DEST_ADDR [pbc|pin] [pin code]\n");
printf("\n\rExample: p2p_connect 00:e0:4c:87:00:15 pin 12345678\n");
return;
}
if (hwaddr_aton(argv[1], dest)){
printf("\r\nP2P_CONNECT: dest address is not correct!\n");
return;
}
//printf("\r\nDEST: %2.2x:%2.2x:%2.2x:%2.2x:%2.2x:%2.2x\n", dest[0], dest[1], dest[2], dest[3], dest[4], dest[5]);
config_method = WPS_PBC;
if(argc == 3) {
if(os_strncmp(argv[2], "pbc", 3) == 0)
config_method = WPS_PBC;
else if(os_strncmp(argv[2], "pin", 3) == 0){
config_method = WPS_PIN_DISPLAY;
}else{
printf("\n\rUnknown config method!\n");
printf("\n\rUsage: p2p_connect DEST_ADDR [pbc|pin] \n");
printf("\n\rExample: p2p_connect 00:e0:4c:87:00:15 pin\n");
return;
}
}
else if(argc == 4) {
if(os_strncmp(argv[2], "pin", 3) == 0){
config_method = WPS_PIN_KEYPAD;
pin = argv[3];
}else{
printf("\n\rUnknown config method!\n");
printf("\n\rUsage: p2p_connect DEST_ADDR [pbc|pin] [pin code]\n");
printf("\n\rExample: p2p_connect 00:e0:4c:87:00:15 pin 12345678\n");
return;
}
}
#else //For test
u8 dest1[ETH_ALEN] = {0xea, 0x92, 0xa4, 0x9b, 0x61, 0xd6}; //NEXUS 4
//u8 dest1[ETH_ALEN] = {0x0e, 0x37, 0xdc, 0xfc, 0xc4, 0x12}; //HUAWEI U9508_c001
//u8 dest1[ETH_ALEN] = {0x42, 0xcb, 0xa8, 0xd3, 0x2c, 0x50}; //HUAWEI G610-T00
os_memcpy(dest, dest1, ETH_ALEN);
config_method = WPS_PBC;
#endif
if (queue_for_p2p_nego!= NULL) {
os_xqueue_delete(queue_for_p2p_nego);
queue_for_p2p_nego = NULL;
}
queue_for_p2p_nego = os_xqueue_create(1, P2P_GO_NEGO_RESULT_SIZE);
if(queue_for_p2p_nego != NULL) {
ret = wifi_cmd_p2p_connect(dest, config_method, pin);
if(ret == 0)
result = os_xqueue_receive(queue_for_p2p_nego, res, 15);
os_xqueue_delete(queue_for_p2p_nego);
queue_for_p2p_nego = NULL;
if((ret == 0) || (result == 0))
wifi_p2p_start_wps(res);
}
}
#endif //CONFIG_ENABLE_P2P

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,75 @@
/**
******************************************************************************
* @file wifi_wps_config.h
* @author
* @version
* @brief This file provides user interfaces for WPS functionality.
******************************************************************************
* @attention
*
* This module is a confidential and proprietary property of RealTek and
* possession or use of this module requires written permission of RealTek.
*
* Copyright(c) 2016, Realtek Semiconductor Corporation. All rights reserved.
******************************************************************************
*/
/** @addtogroup wpsp2p WPS/P2P
* @ingroup wlan
* @brief WPS/P2P functions
* @{
*/
/**
* @brief Start WPS enrollee process.
* @warning Before invoking this function, the Wi-Fi should be enabled by using @ref wifi_on().
* @param[in] wps_config: WPS configure method. Options are: WPS_CONFIG_DISPLAY, WPS_CONFIG_KEYPAD, and WPS_CONFIG_PUSHBUTTON.
* @param[in] pin: PIN number. Can be set to NULL if using WPS_CONFIG_PUSHBUTTON.
* @param[in] channel: Channel. Currently un-used, can be set to 0.
* @param[in] ssid: Target network SSID. Can be set to NULL if no target network specified.
* @return 0 on success.
* @note Please make sure CONFIG_ENABLE_WPS is enabled in platform_opts.h.\n
* You can reference @ref cmd_wps() to know how to choose input parameters.
*/
int wps_start(u16 wps_config, char *pin, u8 channel, char *ssid);
/**
* @brief Command to start WPS enrollee process for commonly use. Can refer to ATWW in atcmd_wifi.c.
* @warning Before invoking this function, the Wi-Fi should be enabled by using @ref wifi_on().
* @param[in] argc: Command line argument. Argument count.
* @param[in] argv: Command line argument. Argument vector.
* @return 0 on success.
* @note Command style for example:
* - cmd_wps pbc
* - cmd_wps pin
* - cmd_wps pin 12345678
* @note Please make sure CONFIG_ENABLE_WPS is enabled in platform_opts.h.
*/
void cmd_wps(int argc, char **argv);
/**
* @brief Start a WPS registrar thread.
* @warning Before invoking this function, the Wi-Fi should be in SoftAP mode.
* @param[in] config_methods: WPS configure method. Options are: WPS_CONFIG_DISPLAY, WPS_CONFIG_KEYPAD, and WPS_CONFIG_PUSHBUTTON.
* @param[in] pin: PIN number. Can be set to NULL.
* @return None
* @note Please make sure CONFIG_ENABLE_WPS and CONFIG_ENABLE_WPS_AP are enabled in platform_opts.h.\n
* You can reference @ref cmd_ap_wps() to know how to choose input parameters.
*/
void wifi_start_ap_wps_thread(u16 config_methods, char *pin);
/**
* @brief Command to start WPS registrar process for commonly use. Can refer to ATWw in atcmd_wifi.c.
* @warning Before invoking this function, the Wi-Fi should be in SoftAP mode.
* @param[in] argc: Command line argument. Argument count.
* @param[in] argv: Command line argument. Argument vector.
* @return 0 on success
* @note Command style for example:
* - cmd_ap_wps pbc
* - cmd_ap_wps pin
* - cmd_ap_wps pin 12345678
* @note Please make sure CONFIG_ENABLE_WPS and CONFIG_ENABLE_WPS_AP are enabled in platform_opts.h.
*/
void cmd_ap_wps(int argc, char **argv);
/*\@}*/

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,272 @@
//----------------------------------------------------------------------------//
#include "wifi/wifi_ind.h"
#include "wifi/wifi_conf.h"
#include "osdep_service.h"
#include "platform_stdlib.h"
/******************************************************
* Constants
******************************************************/
#define WIFI_INDICATE_MSG 0
#define WIFI_MANAGER_STACKSIZE 1300
#define WIFI_MANAGER_PRIORITY (0) //Actual priority is 4 since calling rtw_create_task
#define WIFI_MANAGER_Q_SZ 8
#define WIFI_EVENT_MAX_ROW 3
/******************************************************
* Globals
******************************************************/
static event_list_elem_t event_callback_list[WIFI_EVENT_MAX][WIFI_EVENT_MAX_ROW];
#if CONFIG_WIFI_IND_USE_THREAD
static rtw_worker_thread_t wifi_worker_thread;
#endif
//----------------------------------------------------------------------------//
#if CONFIG_WIFI_IND_USE_THREAD
static rtw_result_t rtw_send_event_to_worker(int event_cmd, char *buf, int buf_len, int flags)
{
rtw_event_message_t message;
int i;
rtw_result_t ret = RTW_SUCCESS;
char *local_buf = NULL;
if(event_cmd >= WIFI_EVENT_MAX)
return RTW_BADARG;
for(i = 0; i < WIFI_EVENT_MAX_ROW; i++){
if(event_callback_list[event_cmd][i].handler == NULL)
continue;
message.function = (event_handler_t)event_callback_list[event_cmd][i].handler;
message.buf_len = buf_len;
if(buf_len){
local_buf = (char*)pvPortMalloc(buf_len);
if(local_buf == NULL)
return RTW_NOMEM;
memcpy(local_buf, buf, buf_len);
//printf("\n!!!!!Allocate %p(%d) for evcmd %d\n", local_buf, buf_len, event_cmd);
}
message.buf = local_buf;
message.flags = flags;
message.user_data = event_callback_list[event_cmd][i].handler_user_data;
ret = rtw_push_to_xqueue(&wifi_worker_thread.event_queue, &message, 0);
if(ret != RTW_SUCCESS){
if(local_buf){
printf("\r\nrtw_send_event_to_worker: enqueue cmd %d failed and free %p(%d)\n", event_cmd, local_buf, buf_len);
vPortFree(local_buf);
}
break;
}
}
return ret;
}
#else
static rtw_result_t rtw_indicate_event_handle(int event_cmd, char *buf, int buf_len, int flags)
{
rtw_event_handler_t handle = NULL;
int i;
if(event_cmd >= WIFI_EVENT_MAX)
return RTW_BADARG;
for(i = 0; i < WIFI_EVENT_MAX_ROW; i++){
handle = event_callback_list[event_cmd][i].handler;
if(handle == NULL)
continue;
handle(buf, buf_len, flags, event_callback_list[event_cmd][i].handler_user_data);
}
return RTW_SUCCESS;
}
#endif
void wifi_indication( rtw_event_indicate_t event, char *buf, int buf_len, int flags)
{
//
// If upper layer application triggers additional operations on receiving of wext_wlan_indicate,
// please strictly check current stack size usage (by using uxTaskGetStackHighWaterMark() )
// , and tries not to share the same stack with wlan driver if remaining stack space is
// not available for the following operations.
// ex: using semaphore to notice another thread.
switch(event)
{
case WIFI_EVENT_DISCONNECT:
#if(WIFI_INDICATE_MSG==1)
printf("\n\r %s():Disconnection indication received", __FUNCTION__);
#endif
break;
case WIFI_EVENT_CONNECT:
// For WPA/WPA2 mode, indication of connection does not mean data can be
// correctly transmitted or received. Data can be correctly transmitted or
// received only when 4-way handshake is done.
// Please check WIFI_EVENT_FOURWAY_HANDSHAKE_DONE event
#if(WIFI_INDICATE_MSG==1)
// Sample: return mac address
if(buf != NULL && buf_len == 6)
{
printf("\n\r%s():Connect indication received: %02x:%02x:%02x:%02x:%02x:%02x", __FUNCTION__,
buf[0],buf[1],buf[2],buf[3],buf[4],buf[5]);
}
#endif
break;
case WIFI_EVENT_FOURWAY_HANDSHAKE_DONE:
#if(WIFI_INDICATE_MSG==1)
if(buf != NULL)
{
if(buf_len == strlen(IW_EXT_STR_FOURWAY_DONE))
printf("\n\r%s():%s", __FUNCTION__, buf);
}
#endif
break;
case WIFI_EVENT_SCAN_RESULT_REPORT:
#if(WIFI_INDICATE_MSG==1)
printf("\n\r%s(): WIFI_EVENT_SCAN_RESULT_REPORT\n", __func__);
#endif
break;
case WIFI_EVENT_SCAN_DONE:
#if(WIFI_INDICATE_MSG==1)
printf("\n\r%s(): WIFI_EVENT_SCAN_DONE\n", __func__);
#endif
break;
case WIFI_EVENT_RECONNECTION_FAIL:
#if(WIFI_INDICATE_MSG==1)
if(buf != NULL){
if(buf_len == strlen(IW_EXT_STR_RECONNECTION_FAIL))
printf("\n\r%s", buf);
}
#endif
break;
case WIFI_EVENT_NO_NETWORK:
#if(WIFI_INDICATE_MSG==1)
printf("\n\r%s(): WIFI_EVENT_NO_NETWORK\n", __func__);
#endif
break;
case WIFI_EVENT_RX_MGNT:
#if(WIFI_INDICATE_MSG==1)
printf("\n\r%s(): WIFI_EVENT_RX_MGNT\n", __func__);
#endif
break;
#if CONFIG_ENABLE_P2P
case WIFI_EVENT_SEND_ACTION_DONE:
#if(WIFI_INDICATE_MSG==1)
printf("\n\r%s(): WIFI_EVENT_SEND_ACTION_DONE\n", __func__);
#endif
break;
#endif //CONFIG_ENABLE_P2P
case WIFI_EVENT_STA_ASSOC:
#if(WIFI_INDICATE_MSG==1)
printf("\n\r%s(): WIFI_EVENT_STA_ASSOC\n", __func__);
#endif
break;
case WIFI_EVENT_STA_DISASSOC:
#if(WIFI_INDICATE_MSG==1)
printf("\n\r%s(): WIFI_EVENT_STA_DISASSOC\n", __func__);
#endif
break;
#ifdef CONFIG_WPS
case WIFI_EVENT_STA_WPS_START:
#if(WIFI_INDICATE_MSG==1)
printf("\n\r%s(): WIFI_EVENT_STA_WPS_START\n", __func__);
#endif
break;
case WIFI_EVENT_WPS_FINISH:
#if(WIFI_INDICATE_MSG==1)
printf("\n\r%s(): WIFI_EVENT_WPS_FINISH\n", __func__);
#endif
break;
case WIFI_EVENT_EAPOL_RECVD:
#if(WIFI_INDICATE_MSG==1)
printf("\n\r%s(): WIFI_EVENT_EAPOL_RECVD\n", __func__);
#endif
break;
#endif
case WIFI_EVENT_BEACON_AFTER_DHCP:
#if(WIFI_INDICATE_MSG==1)
printf("\n\r%s(): WIFI_EVENT_BEACON_AFTER_DHCP\n", __func__);
#endif
break;
case WIFI_EVENT_IP_CHANGED:
#if(WIFI_INDICATE_MSG==1)
printf("\n\r%s(): WIFI_EVENT_IP_CHANNGED\n", __func__);
#endif
break;
case WIFI_EVENT_ICV_ERROR:
#if(WIFI_INDICATE_MSG==1)
printf("\n\r%s(): WIFI_EVENT_ICV_ERROR\n", __func__);
#endif
case WIFI_EVENT_CHALLENGE_FAIL:
#if(WIFI_INDICATE_MSG==1)
printf("\n\r%s(): WIFI_EVENT_CHALLENGE_FAIL\n", __func__);
#endif
break;
}
#if CONFIG_INIC_EN
inic_indicate_event(event, buf, buf_len, flags);
#endif//CONFIG_INIC_EN
#if CONFIG_WIFI_IND_USE_THREAD
rtw_send_event_to_worker(event, buf, buf_len, flags);
#else
rtw_indicate_event_handle(event, buf, buf_len, flags);
#endif
}
void wifi_reg_event_handler(unsigned int event_cmds, rtw_event_handler_t handler_func, void *handler_user_data)
{
int i = 0, j = 0;
if(event_cmds < WIFI_EVENT_MAX){
for(i=0; i < WIFI_EVENT_MAX_ROW; i++){
if(event_callback_list[event_cmds][i].handler == NULL){
for(j=0; j<WIFI_EVENT_MAX_ROW; j++){
if(event_callback_list[event_cmds][j].handler == handler_func){
return;
}
}
event_callback_list[event_cmds][i].handler = handler_func;
event_callback_list[event_cmds][i].handler_user_data = handler_user_data;
return;
}
}
}
}
void wifi_unreg_event_handler(unsigned int event_cmds, rtw_event_handler_t handler_func)
{
int i;
if(event_cmds < WIFI_EVENT_MAX){
for(i = 0; i < WIFI_EVENT_MAX_ROW; i++){
if(event_callback_list[event_cmds][i].handler == handler_func){
event_callback_list[event_cmds][i].handler = NULL;
event_callback_list[event_cmds][i].handler_user_data = NULL;
return;
}
}
}
}
void init_event_callback_list(){
memset(event_callback_list, 0, sizeof(event_callback_list));
}
int wifi_manager_init()
{
#if CONFIG_WIFI_IND_USE_THREAD
rtw_create_worker_thread(&wifi_worker_thread,
WIFI_MANAGER_PRIORITY,
WIFI_MANAGER_STACKSIZE,
WIFI_MANAGER_Q_SZ);
#endif
return 0;
}
void rtw_wifi_manager_deinit()
{
#if CONFIG_WIFI_IND_USE_THREAD
rtw_delete_worker_thread(&wifi_worker_thread);
#endif
}

View File

@@ -0,0 +1,111 @@
/**
******************************************************************************
* @file wifi_ind.h
* @author
* @version
* @brief This file provides the functions related to event handler mechanism.
******************************************************************************
* @attention
*
* This module is a confidential and proprietary property of RealTek and
* possession or use of this module requires written permission of RealTek.
*
* Copyright(c) 2016, Realtek Semiconductor Corporation. All rights reserved.
******************************************************************************
*/
#ifndef _WIFI_INDICATE_H
#define _WIFI_INDICATE_H
/** @addtogroup nic NIC
* @ingroup wlan
* @brief NIC functions
* @{
*/
#include "wifi_conf.h"
typedef void (*rtw_event_handler_t)(char *buf, int buf_len, int flags, void* handler_user_data );
typedef struct
{
// rtw_event_indicate_t event_cmd;
rtw_event_handler_t handler;
void* handler_user_data;
} event_list_elem_t;
/**
* @brief Initialize the event callback list.
* @warning Please make sure this function has been invoked before
* using the event handler related mechanism.
* @param None
* @return None
*/
void init_event_callback_list(void);
/**
* @brief Wlan driver indicate event to upper layer through wifi_indication.
* @param[in] event: An event reported from driver to upper layer application. Please refer to rtw_event_indicate_t enum.
* @param[in] buf: If it is not NUL, buf is a pointer to the buffer for message string.
* @param[in] buf_len: The length of the buffer.
* @param[in] flags: Indicate some extra information, sometimes it is 0.
* @retval None
* @note If upper layer application triggers additional operations on receiving of wext_wlan_indicate,
* please strictly check current stack size usage (by using uxTaskGetStackHighWaterMark() ),
* and tries not to share the same stack with wlan driver if remaining stack space is not available
* for the following operations.
* ex: using semaphore to notice another thread instead of handing event directly in wifi_indication().
* - Wifi event list
*
* 0. WIFI_EVENT_CONNECT : Indicate station connect to AP
* 1. WIFI_EVENT_DISCONNECT : Indicate station disconnect with AP
* 2. WIFI_EVENT_FOURWAY_HANDSHAKE_DONE : Indicate fourway handshake done in station mode when connects to WPA/WPA2 AP.
* 3. WIFI_EVENT_SCAN_RESULT_REPORT : Indicate wifi scan result report event. The event is for application to get the wifi scan result
* 4. WIFI_EVENT_SCAN_DONE : Indicate wifi scan done
* 5. WIFI_EVENT_RECONNECTION_FAIL : Indicate wifi reconnection failed
* 6. WIFI_EVENT_SEND_ACTION_DONE : Indicate the action frame status in p2p. Need to define CONFIG_P2P_NEW in wlan library, default is disable.
* 7. WIFI_EVENT_RX_MGNT : Indicate managerment frame receive
* 8. WIFI_EVENT_STA_ASSOC : Indicate client associate in AP mode
* 9. WIFI_EVENT_STA_DISASSOC : Indicate client disassociate in AP mode
* 10. WIFI_EVENT_STA_WPS_START : Indicate WPS process starting. This event is used in wps process.
* 11. WIFI_EVENT_WPS_FINISH : Indicate WPS process finish. This event is used in wps process.
* 12. WIFI_EVENT_EAPOL_START : Indicate receiving EAPOL_START packets in eap process. This event is used in eap process.
* 13. WIFI_EVENT_EAPOL_RECVD : Indicate receiving EAPOL packets in wps process. This event is used in wps process.
* 14. WIFI_EVENT_NO_NETWORK : Indicate the event that wifi connect failed cause of wifi scan can't scan the specific AP.
* 15. WIFI_EVENT_BEACON_AFTER_DHCP : Indicate station receive beacon after DHCP done. It is used to know the wifi connection is OK by receiving beacon after getting IP.
* 16. WIFI_EVENT_IP_CHANGED : Indicate IP has changed. It is application layer event, it is demoed in example_wifi_roaming.c
* 17. WIFI_EVENT_ICV_ERROR : Indicate that the receiving packets has ICV error.
* 18. WIFI_EVENT_CHALLENGE_FAIL : Indicate authentication failed because of challenge failure
* 19. WIFI_EVENT_MAX : It stands for the end of wifi event.
*/
extern void wifi_indication( rtw_event_indicate_t event, char *buf, int buf_len, int flags);
/**
* @brief Register the event listener.
* @param[in] event_cmds : The event command number indicated.
* @param[in] handler_func : the callback function which will
* receive and process the event.
* @param[in] handler_user_data : user specific data that will be
* passed directly to the callback function.
* @return RTW_SUCCESS : if successfully registers the event.
* @return RTW_ERROR : if an error occurred.
* @note Set the same event_cmds with empty handler_func will
* unregister the event_cmds.
*/
extern void wifi_reg_event_handler(unsigned int event_cmds, rtw_event_handler_t handler_func, void *handler_user_data);
/**
* @brief Un-register the event listener.
* @param[in] event_cmds : The event command number indicated.
* @param[in] handler_func : the callback function which will
* receive and process the event.
*
* @return RTW_SUCCESS : if successfully un-registers the event .
* @return RTW_ERROR : if an error occurred.
*/
extern void wifi_unreg_event_handler(unsigned int event_cmds, rtw_event_handler_t handler_func);
/*\@}*/
#endif //_WIFI_INDICATE_H

View File

@@ -0,0 +1,523 @@
#include "FreeRTOS.h"
#include "task.h"
#include "main.h"
#include "tcpip.h"
#include "wifi/wifi_conf.h"
#ifndef CONFIG_WLAN
#define CONFIG_WLAN 1
#endif
#if CONFIG_WLAN
#include <platform/platform_stdlib.h>
// Add extra interfaces to make release sdk able to determine promisc API linking
void promisc_deinit(void *padapter)
{
#ifdef CONFIG_PROMISC
_promisc_deinit(padapter);
#endif
}
int promisc_recv_func(void *padapter, void *rframe)
{
// Never reach here if not define CONFIG_PROMISC
#ifdef CONFIG_PROMISC
return _promisc_recv_func(padapter, rframe);
#else
return 0;
#endif
}
int promisc_recv_lens_func(void *padapter, u8 *payload, u8 plen)
{
// Never reach here if not define CONFIG_PROMISC
#ifdef CONFIG_PROMISC
#if CONFIG_UNSUPPORT_PLCPHDR_RPT
return _promisc_recv_lens_func(padapter, payload, plen);
#else
return 0;
#endif
#else
return 0;
#endif
}
int promisc_filter_retransmit_pkt(u8 enable, u8 filter_interval_ms)
{
#ifdef CONFIG_PROMISC
#if CONFIG_UNSUPPORT_PLCPHDR_RPT
return _promisc_filter_retransmit_plcp_pkt(enable, filter_interval_ms);
#else
return -1;//_promisc_filter_retransmit_normal_pkt(enable);
#endif
#else
return -1;
#endif
}
int promisc_filter_with_len(u16 len)
{
// Never reach here if not define CONFIG_PROMISC
#ifdef CONFIG_PROMISC
#if CONFIG_UNSUPPORT_PLCPHDR_RPT
return _promisc_filter_with_len(len);
#else
return -1;
#endif
#else
return -1;
#endif
}
int promisc_set(rtw_rcr_level_t enabled, void (*callback)(unsigned char*, unsigned int, void*), unsigned char len_used)
{
#ifdef CONFIG_PROMISC
return _promisc_set(enabled, callback, len_used);
#else
return -1;
#endif
}
unsigned char is_promisc_enabled(void)
{
#ifdef CONFIG_PROMISC
return _is_promisc_enabled();
#else
return 0;
#endif
}
int promisc_get_fixed_channel(void *fixed_bssid, u8 *ssid, int *ssid_length)
{
#ifdef CONFIG_PROMISC
return _promisc_get_fixed_channel(fixed_bssid, ssid, ssid_length);
#else
return 0;
#endif
}
void promisc_filter_by_ap_and_phone_mac(u8 enable, void *ap_mac, void *phone_mac)
{
#ifdef CONFIG_PROMISC
_promisc_filter_by_ap_and_phone_mac(enable, ap_mac, phone_mac);
#endif
}
// End of Add extra interfaces
struct eth_frame {
struct eth_frame *prev;
struct eth_frame *next;
unsigned char da[6];
unsigned char sa[6];
unsigned int len;
unsigned char type;
signed char rssi;
};
#if CONFIG_INIC_CMD_RSP
#if defined(__IAR_SYSTEMS_ICC__)||defined (__GNUC__)
#pragma pack(1)
#endif
struct inic_eth_frame {
unsigned char da[6];
unsigned char sa[6];
unsigned int len;
unsigned char type;
};
#if defined(__IAR_SYSTEMS_ICC__)||defined (__GNUC__)
#pragma pack()
#endif
static struct inic_eth_frame *inic_frame, *inic_frame_tail = NULL;
static int inic_frame_cnt = 0;
#define MAX_INIC_FRAME_NUM 50 //maximum packets for each channel
extern void inic_c2h_msg(const char *atcmd, char status, char *msg, u16 msg_len);
#endif
struct eth_buffer {
struct eth_frame *head;
struct eth_frame *tail;
};
static struct eth_buffer eth_buffer;
#ifdef CONFIG_PROMISC
#define MAX_PACKET_FILTER_INFO 5
#define FILTER_ID_INIT_VALUE 10
rtw_packet_filter_info_t paff_array[MAX_PACKET_FILTER_INFO]={0, 0, 0, 0, 0};
static u8 packet_filter_enable_num = 0;
void promisc_init_packet_filter()
{
int i = 0;
for(i=0; i<MAX_PACKET_FILTER_INFO; i++){
paff_array[i].filter_id = FILTER_ID_INIT_VALUE;
paff_array[i].enable = 0;
paff_array[i].patt.mask_size = 0;
paff_array[i].rule = RTW_POSITIVE_MATCHING;
paff_array[i].patt.mask = NULL;
paff_array[i].patt.pattern = NULL;
}
packet_filter_enable_num = 0;
}
int promisc_add_packet_filter(u8 filter_id, rtw_packet_filter_pattern_t *patt, rtw_packet_filter_rule_t rule)
{
int i = 0;
while(i < MAX_PACKET_FILTER_INFO){
if(paff_array[i].filter_id == FILTER_ID_INIT_VALUE){
break;
}
i++;
}
if(i == MAX_PACKET_FILTER_INFO)
return -1;
paff_array[i].filter_id = filter_id;
paff_array[i].patt.offset= patt->offset;
paff_array[i].patt.mask_size = patt->mask_size;
paff_array[i].patt.mask = pvPortMalloc(patt->mask_size);
memcpy(paff_array[i].patt.mask, patt->mask, patt->mask_size);
paff_array[i].patt.pattern= pvPortMalloc(patt->mask_size);
memcpy(paff_array[i].patt.pattern, patt->pattern, patt->mask_size);
paff_array[i].rule = rule;
paff_array[i].enable = 0;
return 0;
}
int promisc_enable_packet_filter(u8 filter_id)
{
int i = 0;
while(i < MAX_PACKET_FILTER_INFO){
if(paff_array[i].filter_id == filter_id)
break;
i++;
}
if(i == MAX_PACKET_FILTER_INFO)
return -1;
paff_array[i].enable = 1;
packet_filter_enable_num++;
return 0;
}
int promisc_disable_packet_filter(u8 filter_id)
{
int i = 0;
while(i < MAX_PACKET_FILTER_INFO){
if(paff_array[i].filter_id == filter_id)
break;
i++;
}
if(i == MAX_PACKET_FILTER_INFO)
return -1;
paff_array[i].enable = 0;
packet_filter_enable_num--;
return 0;
}
int promisc_remove_packet_filter(u8 filter_id)
{
int i = 0;
while(i < MAX_PACKET_FILTER_INFO){
if(paff_array[i].filter_id == filter_id)
break;
i++;
}
if(i == MAX_PACKET_FILTER_INFO)
return -1;
paff_array[i].filter_id = FILTER_ID_INIT_VALUE;
paff_array[i].enable = 0;
paff_array[i].patt.mask_size = 0;
paff_array[i].rule = 0;
if(paff_array[i].patt.mask){
vPortFree(paff_array[i].patt.mask);
paff_array[i].patt.mask = NULL;
}
if(paff_array[i].patt.pattern){
vPortFree(paff_array[i].patt.pattern);
paff_array[i].patt.pattern = NULL;
}
return 0;
}
#endif
/* Make callback simple to prevent latency to wlan rx when promiscuous mode */
static void promisc_callback(unsigned char *buf, unsigned int len, void* userdata)
{
struct eth_frame *frame = (struct eth_frame *) pvPortMalloc(sizeof(struct eth_frame));
if(frame) {
frame->prev = NULL;
frame->next = NULL;
memcpy(frame->da, buf, 6);
memcpy(frame->sa, buf+6, 6);
frame->len = len;
frame->rssi = ((ieee80211_frame_info_t *)userdata)->rssi;
taskENTER_CRITICAL();
if(eth_buffer.tail) {
eth_buffer.tail->next = frame;
frame->prev = eth_buffer.tail;
eth_buffer.tail = frame;
}
else {
eth_buffer.head = frame;
eth_buffer.tail = frame;
}
taskEXIT_CRITICAL();
}
}
struct eth_frame* retrieve_frame(void)
{
struct eth_frame *frame = NULL;
taskENTER_CRITICAL();
if(eth_buffer.head) {
frame = eth_buffer.head;
if(eth_buffer.head->next) {
eth_buffer.head = eth_buffer.head->next;
eth_buffer.head->prev = NULL;
}
else {
eth_buffer.head = NULL;
eth_buffer.tail = NULL;
}
}
taskEXIT_CRITICAL();
return frame;
}
static void promisc_test(int duration, unsigned char len_used)
{
int ch;
unsigned int start_time;
struct eth_frame *frame;
eth_buffer.head = NULL;
eth_buffer.tail = NULL;
wifi_enter_promisc_mode();
wifi_set_promisc(RTW_PROMISC_ENABLE, promisc_callback, len_used);
for(ch = 1; ch <= 13; ch ++) {
if(wifi_set_channel(ch) == 0)
printf("\n\n\rSwitch to channel(%d)", ch);
start_time = xTaskGetTickCount();
while(1) {
unsigned int current_time = xTaskGetTickCount();
if((current_time - start_time) < (duration * configTICK_RATE_HZ)) {
frame = retrieve_frame();
if(frame) {
int i;
printf("\n\rDA:");
for(i = 0; i < 6; i ++)
printf(" %02x", frame->da[i]);
printf(", SA:");
for(i = 0; i < 6; i ++)
printf(" %02x", frame->sa[i]);
printf(", len=%d", frame->len);
printf(", RSSI=%d", frame->rssi);
#if CONFIG_INIC_CMD_RSP
if(inic_frame_tail){
if(inic_frame_cnt < MAX_INIC_FRAME_NUM){
memcpy(inic_frame_tail->da, frame->da, 6);
memcpy(inic_frame_tail->sa, frame->sa, 6);
inic_frame_tail->len = frame->len;
inic_frame_tail++;
inic_frame_cnt++;
}
}
#endif
vPortFree((void *) frame);
}
else
vTaskDelay(1); //delay 1 tick
}
else
break;
}
#if CONFIG_INIC_CMD_RSP
if(inic_frame){
inic_c2h_msg("ATWM", RTW_SUCCESS, (char *)inic_frame, sizeof(struct inic_eth_frame)*inic_frame_cnt);
memset(inic_frame, '\0', sizeof(struct inic_eth_frame)*MAX_INIC_FRAME_NUM);
inic_frame_tail = inic_frame;
inic_frame_cnt = 0;
rtw_msleep_os(10);
}
#endif
}
wifi_set_promisc(RTW_PROMISC_DISABLE, NULL, 0);
while((frame = retrieve_frame()) != NULL)
vPortFree((void *) frame);
}
static void promisc_callback_all(unsigned char *buf, unsigned int len, void* userdata)
{
struct eth_frame *frame = (struct eth_frame *) pvPortMalloc(sizeof(struct eth_frame));
if(frame) {
frame->prev = NULL;
frame->next = NULL;
#if CONFIG_UNSUPPORT_PLCPHDR_RPT
if(((ieee80211_frame_info_t *)userdata)->type == RTW_RX_UNSUPPORT){
//NOTICE: buf structure now is rtw_rx_info_t.
frame->type = 0xFF;
memset(frame->da, 0, 6);
memset(frame->sa, 0, 6);
}
else
#endif
{
memcpy(frame->da, buf+4, 6);
memcpy(frame->sa, buf+10, 6);
frame->type = *buf;
}
frame->len = len;
/*
* type is the first byte of Frame Control Field of 802.11 frame
* If the from/to ds information is needed, type could be reused as follows:
* frame->type = ((((ieee80211_frame_info_t *)userdata)->i_fc & 0x0100) == 0x0100) ? 2 : 1;
* 1: from ds; 2: to ds
*/
frame->rssi = ((ieee80211_frame_info_t *)userdata)->rssi;
taskENTER_CRITICAL();
if(eth_buffer.tail) {
eth_buffer.tail->next = frame;
frame->prev = eth_buffer.tail;
eth_buffer.tail = frame;
}
else {
eth_buffer.head = frame;
eth_buffer.tail = frame;
}
taskEXIT_CRITICAL();
}
}
static void promisc_test_all(int duration, unsigned char len_used)
{
int ch;
unsigned int start_time;
struct eth_frame *frame;
eth_buffer.head = NULL;
eth_buffer.tail = NULL;
wifi_enter_promisc_mode();
wifi_set_promisc(RTW_PROMISC_ENABLE_2, promisc_callback_all, len_used);
for(ch = 1; ch <= 13; ch ++) {
if(wifi_set_channel(ch) == 0)
printf("\n\n\rSwitch to channel(%d)", ch);
start_time = xTaskGetTickCount();
while(1) {
unsigned int current_time = xTaskGetTickCount();
if((current_time - start_time) < (duration * configTICK_RATE_HZ)) {
frame = retrieve_frame();
if(frame) {
int i;
printf("\n\rTYPE: 0x%x, ", frame->type);
printf("DA:");
for(i = 0; i < 6; i ++)
printf(" %02x", frame->da[i]);
printf(", SA:");
for(i = 0; i < 6; i ++)
printf(" %02x", frame->sa[i]);
printf(", len=%d", frame->len);
printf(", RSSI=%d", frame->rssi);
#if CONFIG_INIC_CMD_RSP
if(inic_frame_tail){
if(inic_frame_cnt < MAX_INIC_FRAME_NUM){
memcpy(inic_frame_tail->da, frame->da, 6);
memcpy(inic_frame_tail->sa, frame->sa, 6);
inic_frame_tail->len = frame->len;
inic_frame_tail->type = frame->type;
inic_frame_tail++;
inic_frame_cnt++;
}
}
#endif
vPortFree((void *) frame);
}
else
vTaskDelay(1); //delay 1 tick
}
else
break;
}
#if CONFIG_INIC_CMD_RSP
if(inic_frame){
inic_c2h_msg("ATWM", RTW_SUCCESS, (char *)inic_frame, sizeof(struct inic_eth_frame)*inic_frame_cnt);
memset(inic_frame, '\0', sizeof(struct inic_eth_frame)*MAX_INIC_FRAME_NUM);
inic_frame_tail = inic_frame;
inic_frame_cnt = 0;
rtw_msleep_os(10);
}
#endif
}
wifi_set_promisc(RTW_PROMISC_DISABLE, NULL, 0);
while((frame = retrieve_frame()) != NULL)
vPortFree((void *) frame);
}
void cmd_promisc(int argc, char **argv)
{
int duration;
#if CONFIG_INIC_CMD_RSP
inic_frame_tail = inic_frame = pvPortMalloc(sizeof(struct inic_eth_frame)*MAX_INIC_FRAME_NUM);
if(inic_frame == NULL){
inic_c2h_msg("ATWM", RTW_BUFFER_UNAVAILABLE_TEMPORARY, NULL, 0);
return;
}
#endif
#ifdef CONFIG_PROMISC
wifi_init_packet_filter();
#endif
if((argc == 2) && ((duration = atoi(argv[1])) > 0))
//promisc_test(duration, 0);
promisc_test_all(duration, 0);
else if((argc == 3) && ((duration = atoi(argv[1])) > 0) && (strcmp(argv[2], "with_len") == 0))
promisc_test(duration, 1);
else
printf("\n\rUsage: %s DURATION_SECONDS [with_len]", argv[0]);
#if CONFIG_INIC_CMD_RSP
if(inic_frame)
vPortFree(inic_frame);
inic_frame_tail = NULL;
inic_frame_cnt = 0;
#endif
}
#endif //#if CONFIG_WLAN

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,21 @@
#ifndef __WIFI_SIMPLE_CONFIG_H
#define __WIFI_SIMPLE_CONFIG_H
/*****************************wifi_simple_config.h****************************/
enum sc_result {
SC_ERROR = -1, /* default error code*/
SC_NO_CONTROLLER_FOUND = 1, /* cannot get sta(controller) in the air which starts a simple config session */
SC_CONTROLLER_INFO_PARSE_FAIL, /* cannot parse the sta's info */
SC_TARGET_CHANNEL_SCAN_FAIL, /* cannot scan the target channel */
SC_JOIN_BSS_FAIL, /* fail to connect to target ap */
SC_DHCP_FAIL, /* fail to get ip address from target ap */
/* fail to create udp socket to send info to controller. note that client isolation
must be turned off in ap. we cannot know if ap has configured this */
SC_UDP_SOCKET_CREATE_FAIL,
SC_TERMINATE,
SC_SUCCESS, /* default success code */
};
int SC_send_simple_config_ack(u8 round);
void print_simple_config_result(enum sc_result sc_code);
#endif //__WIFI_SIMPLE_CONFIG_H

View File

@@ -0,0 +1,117 @@
#ifndef __SIMPLE_CONFIG_H__
#define __SIMPLE_CONFIG_H__
#ifdef __cplusplus
extern "C" {
#endif
/* This macro means user take simple config
* lib to another platform such as linux, and
* have no rom crypto libs of simple config,
* so we take simple_config_crypto as a sw lib
* This macro is used by Realtek internal to generate simple config lib
* Please delete this macro after generation.
*/
#define SIMPLE_CONFIG_PLATFORM_LIB 0
#include "platform_opts.h"
#include "autoconf.h"
/* platform related settings */
#if (defined(CONFIG_PLATFORM_8195A)|| defined(CONFIG_PLATFORM_8711B))
#undef u32
#undef s32
#undef u8
#undef s8
#undef u16
#undef s16
typedef unsigned int u32;
typedef signed int s32;
typedef unsigned char u8;
typedef char s8;
typedef unsigned short int u16;
typedef signed short int s16;
#else
#include "osdep_service.h"
#endif
typedef int (*simple_config_printf_fn) (char const * fmt, ...);
typedef void* (*simple_config_memset_fn) (void *dst0, s32 Val, u32 length);
typedef void* (*simple_config_memcpy_fn) ( void *s1, const void *s2, u32 n );
typedef u32 (*simple_config_strlen_fn) (const char *s);
typedef char * (*simple_config_strcpy_fn) (char *dest, const char *src);
typedef void (*simple_config_free_fn) (u8 *pbuf, u32 sz);
typedef u8* (*simple_config_zmalloc_fn) (u32 sz);
typedef u8* (*simple_config_malloc_fn) (u32 sz);
typedef int (*simple_config_memcmp_fn) (const void *av, const void *bv, u32 len);
typedef u32 (*simple_config_ntohl_fn)(u32 x);
struct simple_config_lib_config {
simple_config_printf_fn printf;
simple_config_memset_fn memset;
simple_config_memcpy_fn memcpy;
simple_config_strlen_fn strlen;
simple_config_strcpy_fn strcpy;
simple_config_free_fn free;
simple_config_zmalloc_fn zmalloc;
simple_config_malloc_fn malloc;
simple_config_memcmp_fn memcmp;
simple_config_ntohl_fn _ntohl;
int *is_promisc_callback_unlock;
};
#pragma pack(1)
struct rtk_test_sc {
/* API exposed to user */
unsigned char ssid[32];
unsigned char password[65];
unsigned int ip_addr;
};
// for softAP mode
typedef enum {
SOFTAP_ERROR = -1,
SOFTAP_INIT,
SOFTAP_RECV_A,
SOFTAP_HANDSHAKE_DONE,
SOFTAP_DECODE_SUCCESS,
} SC_softAP_status;
#pragma pack(1)
typedef struct _SC_softAP_decode_ctx {
u8 nonceA[16];
u8 nonceB[32];
u8 mac[6];
SC_softAP_status softAP_decode_status;
} SC_softAP_decode_ctx;
/* expose data */
extern s32 is_promisc_callback_unlock;
extern u8 g_bssid[6];
extern u8 get_channel_flag;
extern u8 g_security_mode;
/* expose API */
extern s32 rtk_sc_init(char *custom_pin_code, struct simple_config_lib_config* config);
extern int rtl_pre_parse(u8 *mac_addr, u8 *buf, void *userdata, u8 **da, u8 **sa, unsigned int *len);
extern s32 rtk_start_parse_packet(u8 *da, u8 *sa, s32 len, void * user_data, void *backup_sc);
extern SC_softAP_status softAP_simpleConfig_parse(unsigned char *buf, int len, void *backup_sc_ctx, void *psoftAP_ctx);
extern void rtk_restart_simple_config(void);
extern void rtk_sc_deinit();
extern void wifi_enter_promisc_mode();
extern void whc_fix_channel();
extern void whc_unfix_channel();
#ifdef __cplusplus
}
#endif
#endif /* __SIMPLE_CONFIG_H__*/

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,114 @@
#ifndef _UTIL_H
#define _UTIL_H
#include <wireless.h>
#include <wlan_intf.h>
#include <wifi_constants.h>
#include "wifi_structures.h"
#ifdef __cplusplus
extern "C" {
#endif
int wext_get_ssid(const char *ifname, __u8 *ssid);
int wext_set_ssid(const char *ifname, const __u8 *ssid, __u16 ssid_len);
int wext_set_bssid(const char *ifname, const __u8 *bssid);
int wext_get_bssid(const char *ifname, __u8 *bssid);
int wext_set_auth_param(const char *ifname, __u16 idx, __u32 value);
int wext_set_mfp_support(const char *ifname, __u8 value);
#ifdef CONFIG_SAE_SUPPORT
int wext_set_group_id(const char *ifname, __u8 value);
int wext_set_support_wpa3(__u8 enable);
__u8 wext_get_support_wpa3(void);
#endif
#ifdef CONFIG_PMKSA_CACHING
int wext_set_pmk_cache_enable(const char *ifname, __u8 value);
#endif
int wext_set_key_ext(const char *ifname, __u16 alg, const __u8 *addr, int key_idx, int set_tx, const __u8 *seq, __u16 seq_len, __u8 *key, __u16 key_len);
int wext_get_enc_ext(const char *ifname, __u16 *alg, __u8 *key_idx, __u8 *passphrase);
int wext_get_auth_type(const char *ifname, __u32 *auth_type);
int wext_set_passphrase(const char *ifname, const __u8 *passphrase, __u16 passphrase_len);
int wext_get_passphrase(const char *ifname, __u8 *passphrase);
int wext_set_mode(const char *ifname, int mode);
int wext_get_mode(const char *ifname, int *mode);
int wext_set_ap_ssid(const char *ifname, const __u8 *ssid, __u16 ssid_len);
int wext_set_country(const char *ifname, rtw_country_code_t country_code);
int wext_get_rssi(const char *ifname, int *rssi);
int wext_get_snr(const char *ifname, int *snr);
int wext_set_channel(const char *ifname, __u8 ch);
int wext_get_channel(const char *ifname, __u8 *ch);
int wext_register_multicast_address(const char *ifname, rtw_mac_t *mac);
int wext_unregister_multicast_address(const char *ifname, rtw_mac_t *mac);
int wext_set_scan(const char *ifname, char *buf, __u16 buf_len, __u16 flags);
int wext_get_scan(const char *ifname, char *buf, __u16 buf_len);
int wext_set_mac_address(const char *ifname, char * mac);
int wext_get_mac_address(const char *ifname, char * mac);
int wext_enable_powersave(const char *ifname, __u8 lps_mode, __u8 ips_mode);
int wext_disable_powersave(const char *ifname);
int wext_set_tdma_param(const char *ifname, __u8 slot_period, __u8 rfon_period_len_1, __u8 rfon_period_len_2, __u8 rfon_period_len_3);
int wext_set_lps_dtim(const char *ifname, __u8 lps_dtim);
int wext_get_lps_dtim(const char *ifname, __u8 *lps_dtim);
int wext_get_tx_power(const char *ifname, __u8 *poweridx);
int wext_set_txpower(const char *ifname, int poweridx);
int wext_get_associated_client_list(const char *ifname, void * client_list_buffer, __u16 buffer_length);
int wext_get_ap_info(const char *ifname, rtw_bss_info_t * ap_info, rtw_security_t* security);
int wext_mp_command(const char *ifname, char *cmd, int show_msg);
int wext_private_command(const char *ifname, char *cmd, int show_msg);
int wext_private_command_with_retval(const char *ifname, char *cmd, char *ret_buf, int ret_len);
void wext_wlan_indicate(unsigned int cmd, union iwreq_data *wrqu, char *extra);
int wext_set_pscan_channel(const char *ifname, __u8 *ch, __u8 *pscan_config, __u8 length);
int wext_set_autoreconnect(const char *ifname, __u8 mode, __u8 retry_times, __u16 timeout);
int wext_get_autoreconnect(const char *ifname, __u8 *mode);
int wext_set_adaptivity(rtw_adaptivity_mode_t adaptivity_mode);
int wext_set_adaptivity_th_l2h_ini(__u8 l2h_threshold);
int wext_set_trp_tis(__u8 enable);
#if defined(CONFIG_WLAN_LOW_PW)
void wext_set_low_power_mode(__u8 enable);
#endif
int wext_get_auto_chl(const char *ifname, unsigned char *channel_set, unsigned char channel_num);
int wext_set_sta_num(unsigned char ap_sta_num);
int wext_del_station(const char *ifname, unsigned char* hwaddr);
int wext_init_mac_filter(void);
int wext_deinit_mac_filter(void);
int wext_add_mac_filter(unsigned char* hwaddr);
int wext_del_mac_filter(unsigned char* hwaddr);
void wext_set_indicate_mgnt(int enable);
#ifdef CONFIG_CUSTOM_IE
int wext_add_custom_ie(const char *ifname, void * cus_ie, int ie_num);
int wext_update_custom_ie(const char *ifname, void * cus_ie, int ie_index);
int wext_del_custom_ie(const char *ifname);
#endif
#define wext_handshake_done rltk_wlan_handshake_done
int wext_send_mgnt(const char *ifname, char *buf, __u16 buf_len, __u16 flags);
int wext_send_eapol(const char *ifname, char *buf, __u16 buf_len, __u16 flags);
int wext_set_gen_ie(const char *ifname, char *buf, __u16 buf_len, __u16 flags);
void wext_suspend_softap(const char *ifname);
int wext_ap_switch_chl_and_inform(unsigned char new_channel);
int wext_get_nhm_ratio_level(const char *ifname, __u32 *level);
int wext_get_retry_drop_num(const char *ifname, rtw_fw_retry_drop_t * retry);
int wext_get_sw_trx_statistics(const char *ifname, rtw_net_device_stats_t *stats);
void wext_set_indicate_mgnt(int enable);
void wext_set_lowrssi_use_b(int enable,int rssi);
#ifndef CONFIG_MCC_STA_AP_MODE
int wext_get_RxInfo(const char *ifname, __u8* BeaconCnt, int *rssi, __u8* CurIGValue, __u32* Fa_Ofdm_count, __u32* Fa_Cck_count);
int wext_get_RxCrcInfo(const char *ifname, __u32* CCK_Crc_Fail, __u32* CCK_Crc_OK, __u32* OFDM_Crc_Fail, __u32* OFDM_Crc_OK, __u32* HT_Crc_Fail, __u32* HT_Crc_OK);
int wext_get_TxInfo(const char *ifname, __u32 *tx_ok, __u32 *tx_retry, __u32 *tx_drop);
int wext_get_PSInfo(const char *ifname, __u32* tim_wake_up_count);
#endif
#ifdef CONFIG_SYNCPKT
int wext_set_syncpkt_da(const char *ifname, __u8 *da);
int wext_send_syncpkt(const char *ifname, __u8 flag, __u8 pktnum, __u8 interval);
int wext_disable_fw_ips(const char *ifname, __u8 enable);
#endif
int wext_set_adaptivity_enable(const char *ifname, __u8 value);
__u8 wext_get_adaptivity_enable(const char *ifname);
int wext_set_adaptivity_mode(const char *ifname, __u8 mode);
__u8 wext_get_adaptivity_mode(const char *ifname);
__u8 wext_get_channel_plan(const char *ifname);
#ifdef __cplusplus
}
#endif
#endif /* _UTIL_H */