I am working on esp8266. I have builded and flashed the esphttpd webserver.
Then I have added a piece of code to start mdns on esp8266:
static void ICACHE_FLASH_ATTR mdns()
{
struct ip_info ipConfig;
struct mdns_info *info = (struct mdns_info *)os_zalloc(sizeof(struct mdns_info));
wifi_get_ip_info(STATION_IF, &ipConfig);
if (!(wifi_station_get_connect_status() == STATION_GOT_IP && ipConfig.ip.addr != 0)) {
os_printf("Cannot read station configuration\n");
return;
}
info->host_name = (char *) "lienka";
info->ipAddr = ipConfig.ip.addr; //ESP8266 station IP
info->server_name = "module01";
info->server_port = 80;
info->txt_data[0] = "version = now";
info->txt_data[1] = "user1 = data1";
info->txt_data[2] = "user2 = data2";
info->txt_data[3] = "vendor = me";
espconn_mdns_init(info);
//espconn_mdns_server_register();
espconn_mdns_enable();
}
static void ICACHE_FLASH_ATTR testTimerCb(void *arg) {
mdns();
}
In the user_init function the following code was added:
os_timer_disarm(&testTimer);
os_timer_setfn(&testTimer, testTimerCb, NULL);
os_timer_arm(&testTimer, 10000, 0);
The problem is that since I have added the mdns functionality, the esp8266 is restarting every minute. When these 3 lines of code in user_init function is commented out, esp8266 stops restarting itself.
Logs when ESP is restarting:
3fff0e50 already freed
3fff0e50 already freed
Fatal exception 0(IllegalInstructionCause):
epc1=0x40107cba, epc2=0x00000000, epc3=0x00000000, excvaddr=0x00000000, depc=0x00000000
ets Jan 8 2013,rst cause:1, boot mode:(3,0)
load 0x40100000, len 32264, room 16
tail 8
chksum 0x13
load 0x3ffe8000, len 2316, room 0
tail 12
chksum 0x9f
ho 0 tail 12 room 4
load 0x3ffe8910, len 6456, room 12
tail 12
chksum 0x30
csum 0x30
rl⸮⸮rl⸮⸮Httpd init
Could anybody help me, what should I do?
Related
I try to get a program running on OpenWRT (kernel ver.: 4.14.215, musl libc ver.: 1.1.24) which implements RFC8157 (a new tunneling protocol). Unfortunately the guy who wrote it doesn't seem to maintain it anymore.
At some point it writes its first message to a raw ipv6 socket via sendmsg(). Unfortunately sendmsg() returns EACCES. I am pretty new to system programming and do not really have a clue what to look for.
I have tried the following:
#> ls -l /proc/[pid]/fd/*
lrwx------ 1 root root 64 Jan 25 17:41 /proc/22727/fd/0 -> /dev/pts/0
lrwx------ 1 root root 64 Jan 25 17:41 /proc/22727/fd/1 -> /dev/pts/0
lrwx------ 1 root root 64 Jan 25 17:41 /proc/22727/fd/2 -> /dev/pts/0
lrwx------ 1 root root 64 Jan 25 17:41 /proc/22727/fd/3 -> socket:[1293688]
#> ls -l /proc/[pid]/fdinfo/*
pos: 0
flags: 02
mnt_id: 8
So the socket seems to be opened in read/write mode.
lsof lists the socket as well. But for some reason with an ipv6 address of 0.
#> lsof | grep [pid]
openhybri 18018 root 3u raw6 0t0 92469 00000000000000000000000000000000:002F->00000000000000000000000000000000:0000 st=07
The man page lists the attempt to send an UDP packet from a broadcast address to an anycast address as possible cause. But this seems not the case here. A raw IPv6 socket is not a UDP socket (isn't it?) and the src IP is a public one.
Everything is executed as root user.
#> id
uid=0(root) gid=0(root) groups=0(root)
As I am not really sure what to look for, here is the whole function:
sendmsg() is used in the last if statement.
bool send_grecpmessage(uint8_t msgtype, uint8_t tuntype, void *attributes, int attributes_size) {
unsigned char buffer[MAX_PKT_SIZE] = {};
int size = 0;
/* GRE header */
struct grehdr *greh = (struct grehdr *)(buffer + size);
greh->flags_and_version = htons(GRECP_FLAGSANDVERSION);
greh->proto = htons(GRECP_PROTO);
greh->key = htonl(runtime.haap.bonding_key);
size += sizeof(struct grehdr);
/* GRECP header */
struct grecphdr *grecph = (struct grecphdr *)(buffer + size);
grecph->msgtype_and_tuntype = (msgtype << 4) | tuntype;
size += sizeof(struct grecphdr);
/* Add GRECP attributes */
memcpy(buffer + size, attributes, attributes_size);
size += attributes_size;
/* Source & Destination */
struct sockaddr_in6 src = {};
src.sin6_family = AF_INET6;
if (tuntype == GRECP_TUNTYPE_LTE) {
src.sin6_addr = runtime.lte.interface_ip;
} else {
src.sin6_addr = runtime.dsl.interface_ip;
}
struct sockaddr_in6 dst = {};
dst.sin6_family = AF_INET6;
dst.sin6_addr = runtime.haap.ip;
/* Construct control information */
struct msghdr msgh = {};
struct iovec msgiov = {};
struct cmsghdr *c;
struct unp_in_pktinfo {
struct in6_addr ipi6_addr;
int ipi6_ifindex;
} *pi;
msgh.msg_name = &dst;
msgh.msg_namelen = sizeof(struct sockaddr_in6);
msgiov.iov_base = buffer;
msgiov.iov_len = size;
msgh.msg_iov = &msgiov;
msgh.msg_iovlen = 1;
unsigned char control_buf[CMSG_LEN(sizeof(struct unp_in_pktinfo))] = {};
msgh.msg_control = &control_buf;
msgh.msg_controllen = CMSG_LEN(sizeof(struct unp_in_pktinfo));
c = CMSG_FIRSTHDR(&msgh);
c->cmsg_level = IPPROTO_IPV6;
c->cmsg_type = IPV6_PKTINFO;
c->cmsg_len = CMSG_LEN(sizeof(struct unp_in_pktinfo));
pi = (struct unp_in_pktinfo *)CMSG_DATA(c);
pi->ipi6_addr = src.sin6_addr;
msgh.msg_controllen = c->cmsg_len;
bool res = true;
if (memcmp(&src.sin6_addr, "\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0", 16) != 0) {
if (sendmsg(sockfd, &msgh, 0) <= 0) {
logger(LOG_ERROR, "Raw socket send failed: %s\n", strerror(errno));
res = false;
}
} else {
/* if we don't set a source ip, sendmsg() will use the ip of the outgoing interface
** and since the haap doesn't verify source ip's we would still get replies for our hellos
*/
res = false;
}
/* TODO: check if sending failed due to a link failure and call send_grecpnotify_linkfailure if it did */
return res;
}
You need root (or a sufficient subset as capabilities) to perform raw packet io. This is because ability to construct and send or capture arbitrary packets allows you to spoof or intercept traffic that's part of a connection belonging to another user or system network facilities. EACCES is telling you that you don't have sufficient permissions.
The problem was that the ip route wasn't set for the specific address I tried to reach.
ip route add [IP] via [gateway] dev [interface]
solved it.
I am doing a project where I want to write some info to the MT25Q (MT25QL512ABB1EW9-0SIT) flash device from Micron Technology. But when I try to write and read from the first few pages (0-13) I get trash data back. I thought there might be a protected area in the flash so I checked the value of the corresponding bits in the status register and the value corresponds to none of the sectors being protected. Plus none of possible ranges for protected sector correspond to this value either.
I am using zephyr-os which supports the flash device. Here is my code:
#include "MT25Q.h"
#include <flash.h>
struct device *dev = device_get_binding("MT25Q");
struct flash_pages_info myflash;
flash_get_page_info_by_idx(dev, 0, &myflash);
char *test_line = malloc(5);
char *buf = malloc(5);
strcpy(test_line, "test");
size_t page_count = flash_get_page_count(dev);
flash_write_protection_set(dev, false);
for(long i = 0; i < total_pages; i++) {
returnval = flash_get_page_info_by_idx(dev, i, &myflash);
flash_write(dev, myflash.start_offset, test_line, 5);
flash_read(dev, myflash.start_offset, buf, 5);
printk("%s\n", buf);
}
flash_write_protection_set(dev, true);
free(buf);
free(test_line);
return 0;
}
For the the first 15 iterations of the loop I read back some garbage string. And afterwards it works as expected. The device is byte-writeable.
Can someone help me understand why this is happening ? I hope I posted all the required info but just in case:
total_pages = 256
myflash.size = 131072
there is a weird problem as title when using dpdk,
When I use rte_pktmbuf_alloc(struct rte_mempool *) and already verify the return value of rte_pktmbuf_pool_create() is not NULL, the process receive segmentation fault.
Follow
ing message is output of gdb in dpdk source code:
Thread 1 "osw" received signal SIGSEGV, Segmentation fault.
0x00000000005e9f41 in __mempool_generic_get (cache=0x1a7dfc000000000, n=1, obj_table=0x7fffffffdec8, mp=0x101a7df00)at /root/dpdk-20.05/x86_64-native-linuxapp-gcc/include/rte_mempool.h:1449
1449 if (unlikely(cache == NULL || n >= cache->size))
(gdb) p cache
$1 = (struct rte_mempool_cache *) 0x1a7dfc000000000
(gdb) bt
0 0x00000000005e9f41 in __mempool_generic_get (cache=0x1a7dfc000000000, n=1, obj_table=0x7fffffffdeb8, mp=0x101a7df00)
at /root/dpdk-20.05/x86_64-native-linuxapp-gcc/include/rte_mempool.h:1449
1 rte_mempool_generic_get (cache=0x1a7dfc000000000, n=1, obj_table=0x7fffffffdeb8, mp=0x101a7df00)
at /root/dpdk-20.05/x86_64-native-linuxapp-gcc/include/rte_mempool.h:1517
2 rte_mempool_get_bulk (n=1, obj_table=0x7fffffffdeb8, mp=0x101a7df00)
at /root/dpdk-20.05/x86_64-native-linuxapp-gcc/include/rte_mempool.h:1552
3 rte_mempool_get (obj_p=0x7fffffffdeb8, mp=0x101a7df00) at /root/dpdk-20.05/x86_64-native-linuxapp-gcc/include/rte_mempool.h:1578
4 rte_mbuf_raw_alloc (mp=0x101a7df00) at /root/dpdk-20.05/x86_64-native-linuxapp-gcc/include/rte_mbuf.h:586
5 rte_pktmbuf_alloc (mp=0x101a7df00) at /root/dpdk-20.05/x86_64-native-linuxapp-gcc/include/rte_mbuf.h:896
And I dig into rte_mempool.h:
and change line 1449-1450
1449 if (unlikely(cache == NULL || n >= cache->size))
1450 goto ring_dequeue;
to
1449 if (unlikely(cache == NULL))
1450 goto ring_dequeue;
1451 if (unlikely(n >= cache->size))
1452 goto ring_dequeue;
and it also fail at line 1451
the gdb output message after changing:
Thread 1 "osw" received signal SIGSEGV, Segmentation fault.
__mempool_generic_get (cache=0x1a7dfc000000000, n=1, obj_table=0x7fffffffdeb8, mp=0x101a7df00)
at /root/dpdk-20.05/x86_64-native-linuxapp-gcc/include/rte_mempool.h:1451
1451 if (unlikely(n >= cache->size))
(gdb) p cache
$1 = (struct rte_mempool_cache *) 0x1a7dfc000000000
(gdb) bt
0 __mempool_generic_get (cache=0x1a7dfc000000000, n=1, obj_table=0x7fffffffdeb8, mp=0x101a7df00)
at /root/dpdk-20.05/x86_64-native-linuxapp-gcc/include/rte_mempool.h:1451
1 rte_mempool_generic_get (cache=0x1a7dfc000000000, n=1, obj_table=0x7fffffffdeb8, mp=0x101a7df00)
at /root/dpdk-20.05/x86_64-native-linuxapp-gcc/include/rte_mempool.h:1519
2 rte_mempool_get_bulk (n=1, obj_table=0x7fffffffdeb8, mp=0x101a7df00)
at /root/dpdk-20.05/x86_64-native-linuxapp-gcc/include/rte_mempool.h:1554
3 rte_mempool_get (obj_p=0x7fffffffdeb8, mp=0x101a7df00) at /root/dpdk-20.05/x86_64-native-linuxapp-gcc/include/rte_mempool.h:1580
4 rte_mbuf_raw_alloc (mp=0x101a7df00) at /root/dpdk-20.05/x86_64-native-linuxapp-gcc/include/rte_mbuf.h:586
5 rte_pktmbuf_alloc (mp=0x101a7df00) at /root/dpdk-20.05/x86_64-native-linuxapp-gcc/include/rte_mbuf.h:896
6 main (argc=<optimized out>, argv=<optimized out>) at ofpd.c:150
(gdb) p cache->size
Cannot access memory at address 0x1a7dfc000000000
It looks like the memory address “cache” pointer stored is not NULL but it actually is a NULL pointer.
I have no idea that why does the "cache" pointer address be non zero at prefix 4 bytes and zero at postfix 4 bytes.
The DPDK version is 20.05, I also tried 18.11 and 19.11.
OS is CentOS 8.1 kernel is 4.18.0-147.el8.x86_64.
CPU is AMD EPYC 7401P.
#define RING_SIZE 16384
#define NUM_MBUFS 8191
#define MBUF_CACHE_SIZE 512
int main(int argc, char **argv)
{
int ret;
uint16_t portid;
unsigned cpu_id = 1;
struct rte_mempool *tmp;
int arg = rte_eal_init(argc, argv);
if (arg < 0)
rte_exit(EXIT_FAILURE, "Cannot init EAL: %s\n", rte_strerror(rte_errno));
if (rte_lcore_count() < 10)
rte_exit(EXIT_FAILURE, "We need at least 10 cores.\n");
argc -= arg;
argv += arg;
/* Creates a new mempool in memory to hold the mbufs. */
tmp = rte_pktmbuf_pool_create("TMP", NUM_MBUFS, MBUF_CACHE_SIZE, 0, RTE_MBUF_DEFAULT_BUF_SIZE, rte_socket_id());
if (tmp == NULL)
rte_exit(EXIT_FAILURE, "Cannot create mbuf pool, %s\n", rte_strerror(rte_errno));
printf("tmp addr = %x\n", tmp);
struct rte_mbuf *test = rte_pktmbuf_alloc(tmp);
rte_exit(EXIT_FAILURE, "end\n");
}
I have ever faced same problem when using the return pointer of getifaddrs(), it also got segmentation fault, I had to shift the pointer address like
ifa->ifa_addr = (struct sockaddr *)((uintptr_t)(ifa->ifa_addr) >> 32);
and then it can work normally.
Thereforer, I think this is not dpdk specific issue.
Does anyone know this issue?
Thanks.
I am able to run this without any error by modifying your code for
include headers
removed unused variables
add check if the returned value is NULL or not for alloc
Test on:
CPU: Intel(R) Xeon(R) CPU E5-2699
OS: 4.15.0-101-generic
GCC: 7.5.0
DPDK version: 19.11.2, dpdk mainline
Library mode: static
code:
int main(int argc, char **argv)
{
int ret = 0;
struct rte_mempool *tmp;
int arg = rte_eal_init(argc, argv);
if (arg < 0)
rte_exit(EXIT_FAILURE, "Cannot init EAL: %s\n", rte_strerror(rte_errno));
if (rte_lcore_count() < 10)
rte_exit(EXIT_FAILURE, "We need at least 10 cores.\n");
argc -= arg;
argv += arg;
/* Creates a new mempool in memory to hold the mbufs. */
tmp = rte_pktmbuf_pool_create("TMP", NUM_MBUFS, MBUF_CACHE_SIZE, 0, RTE_MBUF_DEFAULT_BUF_SIZE, rte_socket_id());
if (tmp == NULL)
rte_exit(EXIT_FAILURE, "Cannot create mbuf pool, %s\n", rte_strerror(rte_errno));
printf("tmp addr = %p\n", tmp);
struct rte_mbuf *test = rte_pktmbuf_alloc(tmp);
if (test == NULL)
rte_exit(EXIT_FAILURE, "end\n");
return ret;
}
[EDIT-1] based on the comment Brydon Gibson
Note:
As I do not have access to your codebase or working code snippet my suggestion is to lookup any example code from DPDK/examples/l2fwd or DPDK/examples/skeleton and copy the headers for your compilation.
I assume both the author THE and Brydon are different individuals and might be facing similar on the different code bases.
current question claims with DPDK version 20.05, 18.11 and 19.11 the error is reproduced with code snippet.
current answer clearly sates with static linking of the library the same code snippet works
Requested #BrydonGibson to open the ticket with relevant information and environment details as it might be different.
I am trying to pass a large amount of data between threads in C (Raspberry with Debian).
I want to create 32 queues. I need to pass messages of 105 bytes each one. I want to pass 105 bytes each 4 ms to anothe thread for about 20 seconds (30 seconds top).
What I found with posix queues is that I cannot modify mq_msgsize parameter. I can modify mq_maxmsg but if I try to modify the other, queue does not work. It just work with 1024 bytes.
I think I have not understood mq_maxmsg and mq_msgsize parameters. I thought that mq_maxmsg is the number of messages I can store in the queue and mq_msgsize the size of each parameter.
In mq_send function I should pass the buffer I have with a value of 105 bytes.
In mq_receive function I should read 105 bytes each time.
Is this right?
If I try this, send/received does not work. Only with 1024.
This is how I am declaring the queues (I have 32 right now, but all of them are created equally):
#define Q_MOTOR_SIZE 1024
struct mq_attr mq_motor_attr;
mq_motor_attr.mq_flags = 0;
mq_motor_attr.mq_maxmsg = 10000;
mq_motor_attr.mq_msgsize = Q_MOTOR_SIZE; #I tried to change this value by 105
mq_motor_attr.mq_curmsgs = 0;
PR_mq_motor[0] = mq_open(MOTOR_0_Q_NAME, O_CREAT| O_RDONLY| O_NONBLOCK, 0644, &mq_motor_attr);
PR_mq_motor[1] = mq_open(MOTOR_1_Q_NAME, O_CREAT| O_RDONLY| O_NONBLOCK, 0644, &mq_motor_attr);
...
PR_mq_motor[31] = mq_open(MOTOR_31_Q_NAME, O_CREAT| O_RDONLY| O_NONBLOCK, 0644, &mq_motor_attr);
Every time I send a bunch of frames (105 bytes), should I send 1024 or it should work with 105 as packet size?
mq_send(PR_mq_motor[motor_counter], PR_queue_buffer, 1024, 0);
vs
mq_send(PR_mq_motor[motor_counter], PR_queue_buffer, 105, 0);
Same happens in the recevie part. If I try to read 105 instead of 1024, it crashes somewhere during the operation.
What should I do here? In case something needs to be modified on the raspi configuration, it is not a problem.
As #Shawn suggested. I implemented a linked list in order to have the 32 queues I wanted in the beggining.
I created some arrays to keep track of all the mutex to control access and the header of each list.
I think push is working fine but I have some kind of issue while popping elements.
As I said, I want to storage buffers of 8 bytes each one so I created the struct with buffers of 10 to be sure.
int16_t LL_M_Push(uint8_t LL_M_motor, uint8_t *LL_M_frame, uint16_t LL_M_size) {
pthread_mutex_lock(&PR_LL_M_lock[LL_M_motor]);
PR_LL_M_node_t *current = PR_LL_M_head[LL_M_motor];
if (current != NULL) {
while (current->next != NULL) {
current = current->next;
}
/* now we can add a new variable */
current->next = malloc(sizeof(PR_LL_M_node_t));
memcpy(current->next->val, LL_M_frame, LL_M_size);
current->next->next = NULL;
} else {
PR_LL_M_head[LL_M_motor] = malloc(sizeof(PR_LL_M_node_t));
memcpy(PR_LL_M_head[LL_M_motor]->val, LL_M_frame, LL_M_size);
PR_LL_M_head[LL_M_motor]->next = NULL;
}
PR_LL_M_counter[LL_M_motor]++;
pthread_mutex_unlock(&PR_LL_M_lock[LL_M_motor]);
return PR_LL_M_counter[LL_M_motor];
}
int16_t LL_M_Pop(uint8_t LL_M_motor, uint8_t *LL_M_element) {
uint8_t *retval;
PR_LL_M_node_t *next_node = NULL;
pthread_mutex_lock(&PR_LL_M_lock[LL_M_motor]);
if ((PR_LL_M_head[LL_M_motor] == NULL) || (PR_LL_M_counter[LL_M_motor] == 0)) {
pthread_mutex_unlock(&PR_LL_M_lock[LL_M_motor]);
return -1;
}
next_node = PR_LL_M_head[LL_M_motor]->next;
retval = PR_LL_M_head[LL_M_motor]->val;
memcpy(LL_M_element, retval, 10);
PR_LL_M_counter[LL_M_motor]--;
free(PR_LL_M_head[LL_M_motor]);
PR_LL_M_head[LL_M_motor] = next_node;
pthread_mutex_unlock(&PR_LL_M_lock[LL_M_motor]);
return PR_LL_M_counter[LL_M_motor];
}
Do you see something wrong here? Do you need something else?
I've a runtime error in several function when it try to access structure data generally pass as a parameter to the function.
the first instance of the problem is:
signed portBASE_TYPE xQueueGenericReceive( xQueueHandle pxQueue, void * const p\
vBuffer, portTickType xTicksToWait, portBASE_TYPE xJustPeeking )
{
..............
if( pxQueue->uxMessagesWaiting > ( unsigned portBASE_TY\
PE ) 0 )
.......................
}
where pxQueue is a structure:
typedef xQUEUE * xQueueHandle;
with:
typedef struct QueueDefinition
{
signed char *pcHead; /*< Points to the begin\
ning of the queue storage area. */
signed char *pcTail; /*< Points to the byte \
at the end of the queue storage area. Once more byte is allocated than necessa\
ry to store the queue items, this is used as a marker. */
signed char *pcWriteTo; /*< Points to the free \
next place in the storage area. */
signed char *pcReadFrom;
/*< Points to the last \
place that a queued item was read from. */
xList xTasksWaitingToSend; /*< List of tas\
ks that are blocked waiting to post onto this queue. Stored in priority order.\
*/
xList xTasksWaitingToReceive; /*< List of tasks that \
are blocked waiting to read from this queue. Stored in priority order. */
volatile unsigned portBASE_TYPE uxMessagesWaiting;/*< The number of ite\
ms currently in the queue. */
unsigned portBASE_TYPE uxLength; /*< The length of the q\
ueue defined as the number of items it will hold, not the number of bytes. */
unsigned portBASE_TYPE uxItemSize; /*< The size of each it\
ems that the queue will hold. */
signed portBASE_TYPE xRxLock; /*< Stores the number o\
f items received from the queue (removed from the queue) while the queue was lo\
cked. Set to queueUNLOCKED when the queue is not locked. */
signed portBASE_TYPE xTxLock; /*< Stores the number o\
f items transmitted to the queue (added to the queue)
while the queue was locke\
d. Set to qu.......................
}
where pxQueue is a structure:
typedef xQUEUE * xQueueHandle;
with:
typedef struct QueueDefinition
{
signed char *pcHead; /*< Points to the begin\
ning of the queue storage area. */
signed char *pcTail; /*< Points to the byte \
at the end of the queue storage area. Once more byte is allocated than necessa\
ry to store the queue items, this is used as a marker. */
signed char *pcWriteTo; /*< Points to the free \
next place in the storage area. */
signed char *pcReadFrom;
/*< Points to the last \
place that a queued item was read from. */
xList xTasksWaitingToSend; /*< List of tas\
ks that are blocked waiting to post onto this queue. Stored in priority order.\
*/
xList xTasksWaitingToReceive; /*< List of tasks that \
are blocked waiting to read from this queue. Stored in priority order. */
volatile unsigned portBASE_TYPE uxMessagesWaiting;/*< The number of ite\
ms currently in the queue. */
unsigned portBASE_TYPE uxLength; /*< The length of the q\
ueue defined as the number of items it will hold, not the number of bytes. */
unsigned portBASE_TYPE uxItemSize; /*< The size of each it\
ems that the queue will hold. */
signed portBASE_TYPE xRxLock; /*< Stores the number o\
f items received from the queue (removed from the queue) while the queue was lo\
cked. Set to queueUNLOCKED when the queue is not locked. */
signed portBASE_TYPE xTxLock; /*< Stores the number o\
f items transmitted to the queue (added to the queue)
while the queue was locke\
d. Set to queueUNLOCKED when the queue is not locked. */
} xQUEUE;
eueUNLOCKED when the queue is not locked. */
} xQUEUE;
the runtime error is:
.....
COREB: start xQueueGenericReceive
COREB: execption 24 addr 3c00384
COREB: coreb dump stack
COREB: found fp: ff700900
COREB: call frame 0 -12 feb055e2
COREB: call frame 0 -11 00000000
COREB: call frame 0 -9 00000000
COREB: call frame 0 -8 ff7008d0
......
Similarly, I've the same problem with the following function:
void vListRemove( xListItem *pxItemToRemove )
{
xList * pxList;
pxItemToRemove->pxNext->pxPrevious = pxItemToRemove->pxPrevious;
pxItemToRemove->pxPrevious->pxNext = pxItemToRemove->pxNext;
}
where pxItemToRemove->pxPrevious can be read but not pxItemToRemove->pxNext->pxPrevious
it structure is:
struct xLIST_ITEM
{
portTickType xItemValue; /*< The value b\
eing listed. In most cases this is used to sort the list in descending order. \
*/
volatile struct xLIST_ITEM * pxNext; /*< Pointer to the next xListIt\
em in the list. */
volatile struct xLIST_ITEM * pxPrevious;/*< Pointer to the previous xLi\
stItem in the list. */
void * pvOwner; /*< Poi\
nter to the object (normally a TCB) that contains the list item. There is ther\
efore a two way link between the object containing the list item and the list i\
tem itself. */
void * pvContainer; /*< Poi\
nter to the list in which this list item is placed (if any). */
};
typedef struct xLIST_ITEM xListItem; /* For some reason lint wants t\
his as two separate definitions. */
the runtime error is:
COREB: got to vTaskDelete
COREB: pxTCB GLI prev: a5a5a5a5
COREB: sent to list: 3d02004
COREB: list_rem px prev: a5a5a5a5
COREB: execption 24 addr 3c05444
COREB: coreb dump stack
COREB: found fp: ff7008fc
COREB: call frame 0 -12 feb055e2
COREB: call frame 0 -11 00000000
COREB: call frame 0 -9 00000000
COREB: call frame 0 -8 ff7008cc
COREB: call frame 0 -7 ff700ff4
Thank you in advance.
William
Debugging further with gdb I've got pxQueue:
p/x *pxQueue
$9 = {pcHead = 0xadadadad, pcTail = 0xadadadad, pcWriteTo = 0xadadadad,
pcReadFrom = 0xadadadad, xTasksWaitingToSend = {
uxNumberOfItems = 0xadadadad, pxIndex = 0xadadadad, xListEnd = {
xItemValue = 0xadad, pxNext = 0xadadadad, pxPrevious = 0xadadadad}},
xTasksWaitingToReceive = {uxNumberOfItems = 0xadadadad,
pxIndex = 0xadadadad, xListEnd = {xItemValue = 0xadad,
pxNext = 0xadadadad, pxPrevious = 0xadadadad}},
uxMessagesWaiting = 0xadadadad, uxLength = 0xadadadad,
uxItemSize = 0xadadadad, xRxLock = 0xadadadad, xTxLock = 0xadadadad}
it is really strange, all the parameters of the structure have the same value: 0xadadadad
when I debug further and look at the semaphore creation as a queue object in the create queue function I've got normal values:
p *pxNewQueue
$7 = {pcHead = 0x3d17000 "", pcTail = 0x3d17000 "", pcWriteTo = 0x3d17000 "",
pcReadFrom = 0x3d17000 "", xTasksWaitingToSend = {uxNumberOfItems = 0,
pxIndex = 0x3d16018, xListEnd = {xItemValue = 65535, pxNext = 0x3d16018,
pxPrevious = 0x3d16018}}, xTasksWaitingToReceive = {uxNumberOfItems = 0,
pxIndex = 0x3d1602c, xListEnd = {xItemValue = 65535, pxNext = 0x3d1602c,
pxPrevious = 0x3d1602c}}, uxMessagesWaiting = 0, uxLength = 1,
uxItemSize = 0, xRxLock = -1, xTxLock = -1}
Thanks,
William
What is it you are trying to do, and how. What is COREB?
Are the functions from which you have posted snippets of code unmodified from the official FreeRTOS code? The code is normally compiled and linked into an executable, so you would not get any such run-time error. If there was any problem you would only get compile/link errors. If you are getting run-time errors then are you trying to interpret the code rather than compile it?
I Found the answer,
Basically as they was no doc in FreeRTOS about it, I used gdb and look for the pvParameter during task creation and look where it has been stored in the stack. then when I trigger the task with the taskhook function I give back the parameter:
void *param = *(pxCurrentTCB->pxTopOfStack+31);
// xTaskCallApplicationTaskHook( pxCurrentTCB, pxCurrent\
TCB->pxTopOfStack);
xTaskCallApplicationTaskHook( pxCurrentTCB,param );
then when the queue and lis for the semafor are called, it point to the right address. and the data structure is retrieved.