void ant_process_poll() { process_poll(&ant_process); }
/*---------------------------------------------------------------------------*/ static int input_byte(uint8_t byte) { int crc; if(timer_expired(&rxstate.timer)) { restart_input(); } PT_BEGIN(&rxstate.pt); /* The first incoming byte is the length of the packet. */ rxstate.receiving = 1; rxstate.len = byte; if(byte == 0) { #if DEBUG printf("Bad len 0, state %d rxbytes %d\n", state(), read_rxbytes()); #endif /* DEBUG */ flushrx(); PT_EXIT(&rxstate.pt); } timer_set(&rxstate.timer, PACKET_LIFETIME); for(rxstate.ptr = 0; rxstate.ptr < rxstate.len; rxstate.ptr++) { /* Wait for the next data byte to be received. */ PT_YIELD(&rxstate.pt); rxstate.buf[rxstate.ptr] = byte; } /* Receive two more bytes from the FIFO: the RSSI value and the LQI/CRC */ PT_YIELD(&rxstate.pt); rxstate.buf[rxstate.ptr] = byte; rxstate.ptr++; PT_YIELD(&rxstate.pt); rxstate.buf[rxstate.ptr] = byte; crc = (byte & 0x80); rxstate.ptr++; if(crc == 0) { #if DEBUG printf("bad crc\n"); #endif /* DEBUG */ flushrx(); } else if(packet_rx_len > 0) { #if DEBUG printf("Packet in the buffer (%d), dropping %d bytes\n", packet_rx_len, rxstate.len); #endif /* DEBUG */ flushrx(); process_poll(&cc1101_process); } else if(rxstate.len < ACK_LEN) { /* Drop packets that are way too small: less than ACK_LEN (3) bytes long. */ #if DEBUG printf("!"); #endif /* DEBUG */ } else { /* Read out the first three bytes to determine if we should send an ACK or not. */ /* Send a link-layer ACK before reading the full packet. */ if(rxstate.len >= ACK_LEN) { /* Try to parse the incoming frame as a 802.15.4 header. */ frame802154_t info154; if(frame802154_parse(rxstate.buf, rxstate.len, &info154) != 0) { /* XXX Potential optimization here: we could check if the frame is destined for us, or for the broadcast address and discard the packet if it isn't for us. */ if(1) { /* For dataframes that has the ACK request bit set and that is destined for us, we send an ack. */ if(info154.fcf.frame_type == FRAME802154_DATAFRAME && info154.fcf.ack_required != 0 && rimeaddr_cmp((rimeaddr_t *)&info154.dest_addr, &rimeaddr_node_addr)) { send_ack(info154.seq); /* Make sure that we don't put the radio in the IDLE state before the ACK has been fully transmitted. */ BUSYWAIT_UNTIL((state() != CC1101_STATE_TX), RTIMER_SECOND / 10); ENERGEST_OFF(ENERGEST_TYPE_TRANSMIT); ENERGEST_ON(ENERGEST_TYPE_LISTEN); if(state() == CC1101_STATE_TX) { #if DEBUG printf("didn't end ack tx (in %d, txbytes %d)\n", state(), txbytes()); #endif /* DEBUG */ check_txfifo(); flushrx(); } } memcpy((void *)packet_rx, rxstate.buf, rxstate.len + AUX_LEN); packet_rx_len = rxstate.len + AUX_LEN; /* including AUX */ process_poll(&cc1101_process); #if DEBUG printf("#"); #endif /* DEBUG */ } } } } rxstate.receiving = 0; PT_END(&rxstate.pt); }
/*---------------------------------------------------------------------------*/ void sensors_changed(const struct sensors_sensor *s) { sensors_flags[get_sensor_index(s)] |= FLAG_CHANGED; process_poll(&sensors_process); }
/* Upper half does the polling. */ static u16_t slip_poll_handler(u8_t *outbuf, u16_t blen) { /* This is a hack and won't work across buffer edge! */ if(rxbuf[begin] == 'C') { int i; if(begin < end && (end - begin) >= 6 && memcmp(&rxbuf[begin], "CLIENT", 6) == 0) { state = STATE_TWOPACKETS; /* Interrupts do nothing. */ memset(&rxbuf[begin], 0x0, 6); rxbuf_init(); for(i = 0; i < 13; i++) { slip_arch_writeb("CLIENTSERVER\300"[i]); } return 0; } } /* * Interrupt can not change begin but may change pkt_end. * If pkt_end != begin it will not change again. */ if(begin != pkt_end) { u16_t len; if(begin < pkt_end) { len = pkt_end - begin; if(len > blen) { len = 0; } else { memcpy(outbuf, &rxbuf[begin], len); } } else { len = (RX_BUFSIZE - begin) + (pkt_end - 0); if(len > blen) { len = 0; } else { unsigned i; for(i = begin; i < RX_BUFSIZE; i++) { *outbuf++ = rxbuf[i]; } for(i = 0; i < pkt_end; i++) { *outbuf++ = rxbuf[i]; } } } /* Remove data from buffer together with the copied packet. */ begin = pkt_end; if(state == STATE_TWOPACKETS) { pkt_end = end; state = STATE_OK; /* Assume no bytes where lost! */ /* One more packet is buffered, need to be polled again! */ process_poll(&slip_process); } return len; } return 0; }
static void spiCScallBack(uint8_t port, uint8_t pin){ GPIO_CLEAR_INTERRUPT(SPI0_CS_PORT_BASE, SPI0_CS_PIN_MASK); spi_cs_int = 1; process_poll(&spiProcess); }
/*---------------------------------------------------------------------------*/ PROCESS_THREAD(mainProcess, ev, data) { PROCESS_BEGIN(); GPIO_SET_OUTPUT(GPIO_A_BASE, 0xf8); GPIO_SET_OUTPUT(GPIO_B_BASE, 0x0f); GPIO_SET_OUTPUT(GPIO_C_BASE, 0x02); GPIO_CLR_PIN(GPIO_A_BASE, 0xf8); GPIO_CLR_PIN(GPIO_B_BASE, 0x07); GPIO_SET_PIN(EDISON_WAKEUP_BASE, EDISON_WAKEUP_PIN_MASK); // edison WAKEUP GPIO_SET_INPUT(RESET_PORT_BASE, RESET_PIN_MASK); // reset ioc_set_over(RESET_PORT, RESET_PIN, IOC_OVERRIDE_PUE); leds_off(LEDS_RED); leds_off(LEDS_GREEN); leds_off(LEDS_BLUE); // RESET interrupt, active low GPIO_DETECT_EDGE(RESET_PORT_BASE, RESET_PIN_MASK); GPIO_DETECT_FALLING(RESET_PORT_BASE, RESET_PIN_MASK); GPIO_TRIGGER_SINGLE_EDGE(RESET_PORT_BASE, RESET_PIN_MASK); gpio_register_callback(resetcallBack, RESET_PORT, RESET_PIN); GPIO_ENABLE_INTERRUPT(RESET_PORT_BASE, RESET_PIN_MASK); nvic_interrupt_enable(RESET_NVIC_PORT); GPIO_CLR_PIN(TRIUMVI_DATA_READY_PORT_BASE, TRIUMVI_DATA_READY_MASK); // SPI CS interrupt GPIO_DETECT_EDGE(SPI0_CS_PORT_BASE, SPI0_CS_PIN_MASK); GPIO_DETECT_RISING(SPI0_CS_PORT_BASE, SPI0_CS_PIN_MASK); GPIO_TRIGGER_SINGLE_EDGE(SPI0_CS_PORT_BASE, SPI0_CS_PIN_MASK); gpio_register_callback(spiCScallBack, SPI0_CS_PORT, SPI0_CS_PIN); GPIO_ENABLE_INTERRUPT(SPI0_CS_PORT_BASE, SPI0_CS_PIN_MASK); // SPI interface spix_slave_init(SPIDEV); spix_txdma_enable(SPIDEV); spi_register_callback(spiFIFOcallBack); spix_interrupt_enable(SPIDEV, SSI_IM_RXIM_M); // RX FIFO half full nvic_interrupt_enable(NVIC_INT_SSI0); // uDMA SPI0 TX udma_channel_disable(CC2538_SPI0_TX_DMA_CHAN); udma_channel_prio_set_default(CC2538_SPI0_TX_DMA_CHAN); udma_channel_use_primary(CC2538_SPI0_TX_DMA_CHAN); udma_channel_use_single(CC2538_SPI0_TX_DMA_CHAN); udma_channel_mask_clr(CC2538_SPI0_TX_DMA_CHAN); udma_set_channel_dst(CC2538_SPI0_TX_DMA_CHAN, SPI0DR); udma_set_channel_assignment(CC2538_SPI0_TX_DMA_CHAN, UDMA_CH11_SSI0TX); simple_network_set_callback(&rf_rx_handler); //NETSTACK_RADIO.off(); process_start(&decryptProcess, NULL); process_start(&spiProcess, NULL); while (1){ PROCESS_YIELD(); // buffer is not empty, spi is not in use //if ((spiInUse==0) && (spix_busy(SPIDEV)==0) && ((triumviAvailIDX!=triumviFullIDX) || (triumviRXBufFull==1))){ if ((spiInUse==0) && ((triumviAvailIDX!=triumviFullIDX) || (triumviRXBufFull==1))){ GPIO_SET_PIN(TRIUMVI_DATA_READY_PORT_BASE, TRIUMVI_DATA_READY_MASK); if (triumviRXBufFull==1){ resetCnt += 1; if (resetCnt==RESET_THRESHOLD){ watchdog_reboot(); } } #ifdef LED_DEBUG leds_off(LEDS_RED); leds_off(LEDS_GREEN); leds_off(LEDS_BLUE); #endif } // Fail safe, CC2538 missing some SPI commands, reset spi state else if (triumviRXBufFull==1){ spiState = SPI_RESET; process_poll(&spiProcess); #ifdef LED_DEBUG leds_off(LEDS_RED); leds_off(LEDS_GREEN); leds_on(LEDS_BLUE); #endif } } PROCESS_END(); }
/*---------------------------------------------------------------------------*/ int main(void) { clock_init(); #if UIP_CONF_IPV6 /* A hard coded address overrides the stack default MAC address to allow multiple instances. uip6.c defines it as {0x00,0x06,0x98,0x00,0x02,0x32} giving an ipv6 address of [fe80::206:98ff:fe00:232] We make it simpler, {0x02,0x00,0x00 + the last three bytes of the hard coded address (if any are nonzero). HARD_CODED_ADDRESS can be defined in the contiki-conf.h file, or here to allow quick builds using different addresses. If HARD_CODED_ADDRESS has a prefix it also applied, unless built as a RPL end node. E.g. bbbb::12:3456 becomes fe80::ff:fe12:3456 and prefix bbbb::/64 if non-RPL ::10 becomes fe80::ff:fe00:10 and prefix awaits RA or RPL formation bbbb:: gives an address of bbbb::206:98ff:fe00:232 if non-RPL */ #ifdef HARD_CODED_ADDRESS { uip_ipaddr_t ipaddr; uiplib_ipaddrconv(HARD_CODED_ADDRESS, &ipaddr); if((ipaddr.u8[13] != 0) || (ipaddr.u8[14] != 0) || (ipaddr.u8[15] != 0)) { if(sizeof(uip_lladdr) == 6) { /* Minimal-net uses ethernet MAC */ uip_lladdr.addr[0] = 0x02; uip_lladdr.addr[1] = 0; uip_lladdr.addr[2] = 0; uip_lladdr.addr[3] = ipaddr.u8[13]; uip_lladdr.addr[4] = ipaddr.u8[14]; uip_lladdr.addr[5] = ipaddr.u8[15]; } } } #endif /* HARD_CODED_ADDRESS */ #endif /* UIP_CONF_IPV6 */ process_init(); /* procinit_init initializes RPL which sets a ctimer for the first DIS */ /* We must start etimers and ctimers,before calling it */ process_start(&etimer_process, NULL); ctimer_init(); #if RPL_BORDER_ROUTER process_start(&border_router_process, NULL); printf("Border Router Process started\n"); #elif UIP_CONF_IPV6_RPL printf("RPL enabled\n"); #endif procinit_init(); autostart_start(autostart_processes); /* Set default IP addresses if not specified */ #if !UIP_CONF_IPV6 { uip_ipaddr_t addr; uip_gethostaddr(&addr); if(addr.u8[0] == 0) { uip_ipaddr(&addr, 172,18,0,2); } printf("IP Address: %d.%d.%d.%d\n", uip_ipaddr_to_quad(&addr)); uip_sethostaddr(&addr); uip_getnetmask(&addr); if(addr.u8[0] == 0) { uip_ipaddr(&addr, 255,255,0,0); uip_setnetmask(&addr); } printf("Subnet Mask: %d.%d.%d.%d\n", uip_ipaddr_to_quad(&addr)); uip_getdraddr(&addr); if(addr.u8[0] == 0) { uip_ipaddr(&addr, 172,18,0,1); uip_setdraddr(&addr); } printf("Def. Router: %d.%d.%d.%d\n", uip_ipaddr_to_quad(&addr)); } #else /* UIP_CONF_IPV6 */ #if !UIP_CONF_IPV6_RPL { uip_ipaddr_t ipaddr; #ifdef HARD_CODED_ADDRESS uiplib_ipaddrconv(HARD_CODED_ADDRESS, &ipaddr); #else uip_ip6addr(&ipaddr, 0xaaaa, 0, 0, 0, 0, 0, 0, 0); #endif if((ipaddr.u16[0] != 0) || (ipaddr.u16[1] != 0) || (ipaddr.u16[2] != 0) || (ipaddr.u16[3] != 0)) { #if UIP_CONF_ROUTER if(!uip_ds6_prefix_add(&ipaddr, UIP_DEFAULT_PREFIX_LEN, 0, 0, 0, 0)) { fprintf(stderr,"uip_ds6_prefix_add() failed.\n"); exit(EXIT_FAILURE); } #else /* UIP_CONF_ROUTER */ if(!uip_ds6_prefix_add(&ipaddr, UIP_DEFAULT_PREFIX_LEN, 0)) { fprintf(stderr,"uip_ds6_prefix_add() failed.\n"); exit(EXIT_FAILURE); } #endif /* UIP_CONF_ROUTER */ uip_ds6_set_addr_iid(&ipaddr, &uip_lladdr); uip_ds6_addr_add(&ipaddr, 0, ADDR_AUTOCONF); } } #endif /* !UIP_CONF_IPV6_RPL */ #endif /* !UIP_CONF_IPV6 */ // procinit_init(); // autostart_start(autostart_processes); /* Make standard output unbuffered. */ setvbuf(stdout, (char *)NULL, _IONBF, 0); printf("\n*******%s online*******\n",CONTIKI_VERSION_STRING); #if UIP_CONF_IPV6 && !RPL_BORDER_ROUTER /* Border router process prints addresses later */ { int i = 0; int interface_count = 0; for(i = 0; i < UIP_DS6_ADDR_NB; i++) { if(uip_ds6_if.addr_list[i].isused) { printf("IPV6 Addresss: "); sprint_ip6(uip_ds6_if.addr_list[i].ipaddr); printf("\n"); interface_count++; } } assert(0 < interface_count); } #endif while(1) { fd_set fds; int n; struct timeval tv; clock_time_t next_event; n = process_run(); next_event = etimer_next_expiration_time() - clock_time(); #if DEBUG_SLEEP if(n > 0) printf("sleep: %d events pending\n",n); else printf("sleep: next event @ T-%.03f\n",(double)next_event / (double)CLOCK_SECOND); #endif #ifdef __CYGWIN__ /* wpcap doesn't appear to support select, so * we can't idle the process on windows. */ next_event = 0; #endif if(next_event > (CLOCK_SECOND * 2)) next_event = CLOCK_SECOND * 2; tv.tv_sec = n ? 0 : (next_event / CLOCK_SECOND); tv.tv_usec = n ? 0 : ((next_event % 1000) * 1000); FD_ZERO(&fds); FD_SET(STDIN_FILENO, &fds); #ifdef __CYGWIN__ select(1, &fds, NULL, NULL, &tv); #else FD_SET(tapdev_fd(), &fds); if(0 > select(tapdev_fd() + 1, &fds, NULL, NULL, &tv)) { perror("Call to select() failed."); exit(EXIT_FAILURE); } #endif if(FD_ISSET(STDIN_FILENO, &fds)) { char c; if(read(STDIN_FILENO, &c, 1) > 0) { serial_line_input_byte(c); } } #ifdef __CYGWIN__ process_poll(&wpcap_process); #else process_poll(&tapdev_process); #endif etimer_request_poll(); } return 0; }
PROCESS_THREAD(decryptProcess, ev, data) { PROCESS_BEGIN(); // AES static uint8_t myMic[8] = {0x0}; static uint8_t myNonce[13] = {0}; static uint8_t aes_key[] = AES_KEY; aes_load_keys(aes_key, AES_KEY_STORE_SIZE_KEY_SIZE_128, 1, 0); static uint8_t srcExtAddr[8]; static uint8_t packetPayload[128]; static uint8_t packetDuplicated[123]; static uint8_t* cData = packetDuplicated; static uint8_t* aData = srcExtAddr; uint8_t *packet_hdr; uint8_t *packet_ptr; uint16_t packet_length; uint8_t src_addr_len; uint8_t auth_res; uint8_t myPDATA_LEN; uint16_t i, j, k; uint8_t tmp; packet_header_t rx_pkt_header; while(1){ PROCESS_YIELD(); #ifndef LED_DEBUG leds_on(LEDS_RED); #else leds_on(LEDS_RED); leds_on(LEDS_GREEN); leds_on(LEDS_BLUE); #endif // Get data from radio buffer and parse it packet_hdr = packetbuf_hdrptr(); packet_ptr = packetbuf_dataptr(); packet_length = packetbuf_datalen(); process_packet_header(&rx_pkt_header, packet_hdr); memcpy(packetPayload, packet_ptr, packet_length); src_addr_len = rx_pkt_header.pkt_src_addr_len; // data format: // 1 bytes ID, // 8 bytes source addr, // 4 bytes power, // 1 bytes status reg // 2 bytes panel/circuit ID (optional) // 4 bytes pf (optional) // 4 bytes VRMS (optional) // 4 bytes IRMS (optional) // RX buffer is not full if (triumviRXBufFull==0){ triumviRXPackets[triumviAvailIDX].length = 1; if (src_addr_len>0){ for (i=0; i<src_addr_len; i++){ srcExtAddr[i] = rx_pkt_header.pkt_src_addr[src_addr_len - 1 - i]; triumviRXPackets[triumviAvailIDX].payload[1+i] = srcExtAddr[i]; } triumviRXPackets[triumviAvailIDX].length += src_addr_len; } // Decrypt packet if (packet_ptr[0]==TRIUMVI_PKT_IDENTIFIER){ memcpy(myNonce, srcExtAddr, 8); memcpy(&myNonce[9], &packetPayload[1], 4); // Nonce[8] should be 0 for (i=0; i<POSSIBLE_PKT_LEN_COMBINATION; i++){ myPDATA_LEN = possible_packet_length[i]; memcpy(packetDuplicated, &packetPayload[5], packet_length-5); ccm_auth_decrypt_start(LEN_LEN, 0, myNonce, aData, ADATA_LEN, cData, (myPDATA_LEN+MIC_LEN), MIC_LEN, NULL); while (ccm_auth_decrypt_check_status()!=AES_CTRL_INT_STAT_RESULT_AV){} auth_res = ccm_auth_decrypt_get_result(cData, myPDATA_LEN+MIC_LEN, myMic, MIC_LEN); if (auth_res==CRYPTO_SUCCESS) break; } // succefully decoded the packet, pack the data into buffer if (auth_res==CRYPTO_SUCCESS){ triumviRXPackets[triumviAvailIDX].payload[0] = packet_ptr[0]; tmp = triumviRXPackets[triumviAvailIDX].length; for (i=0; i<4; i++){ triumviRXPackets[triumviAvailIDX].payload[tmp+i] = cData[i]; } triumviRXPackets[triumviAvailIDX].payload[tmp+4] = cData[4]; // Status register j = 5; k = 5; if (cData[4]&BATTERYPACK_STATUSREG){ triumviRXPackets[triumviAvailIDX].payload[tmp+j] = cData[k]; // Panel ID triumviRXPackets[triumviAvailIDX].payload[tmp+j+1] = cData[k+1]; // Circuit ID triumviRXPackets[triumviAvailIDX].length += 2; j += 2; k += 2; } // PF, VRMS, IRMS if (cData[4]&POWERFACTOR_STATUSREG){ for (i=0; i<6; i++){ triumviRXPackets[triumviAvailIDX].payload[tmp+j+i] = cData[k+i]; } triumviRXPackets[triumviAvailIDX].length += 6; } // base length triumviRXPackets[triumviAvailIDX].length += 5; // check if fifo is full if (((triumviAvailIDX == TRIUMVI_PACKET_BUF_LEN-1) && (triumviFullIDX == 0)) || ((triumviAvailIDX != TRIUMVI_PACKET_BUF_LEN-1) && (triumviFullIDX == triumviAvailIDX+1))){ triumviRXBufFull = 1; #ifndef LED_DEBUG leds_on(LEDS_GREEN); #endif } // advance pointer if (triumviAvailIDX == TRIUMVI_PACKET_BUF_LEN-1) triumviAvailIDX = 0; else triumviAvailIDX += 1; } } } #ifndef LED_DEBUG leds_off(LEDS_RED); #endif process_poll(&mainProcess); } PROCESS_END(); }
void dc_electronic_load_setup() { setCurrentMilliamps = 0; readCurrentMilliamps = 0; readMilliVolts = 0; setRateIndex = 0; readCurrentMilliampsDisplay = DISPLAY_MILLI; gfxState = GFX_STATE_MEASURE; dma_ring_buffer_init(&g_debugUsartDmaInputRingBuffer, DEBUG_USART_RX_DMA_CH, g_debugUsartRxBuffer, DEBUG_USART_RX_BUFFER_SIZE); debug_setup(); debug_write_line("?BEGIN setup"); process_init(); process_start(&etimer_process, NULL); process_start(&debug_process, NULL); #ifdef DISP6800_ENABLE process_start(&gfx_update_process, NULL); process_poll(&gfx_update_process); #endif spi_setup(); #ifdef DISP6800_ENABLE disp6800_setup(); gfx_setup(); #endif #ifdef ENCODER_ENABLE encoder_setup(); #endif #ifdef FLASH_ENABLE flashsst25_setup(); #endif #ifdef MAC_ENABLE mac25aa02e48_setup(); mac25aa02e48_read_eui48(); #endif #ifdef ADC_ENABLE adc_setup(); #endif #ifdef DAC_ENABLE dac_setup(); dac_set(0); #endif #ifdef NETWORK_ENABLE network_setup(EUI48); #endif #ifdef FAN_ENABLE fan_setup(); #endif #ifdef BUTTONS_ENABLE buttons_setup(); #endif time_setup(); recorder_setup(); debug_write_line("?END setup"); }
/*---------------------------------------------------------------------------*/ void schedule() { struct sch_process *p = NULL; uint16_t map = run_queues->arrays->map; uint16_t *pmap = &(run_queues->arrays->map); uint8_t ret = 100; struct sch_process *tmp_sch_process = NULL; #if(0) // testing the map operation function uint8_t i = 15; map = 0x01<<i; ret = check_map(map); // set the map, attend to get i here printf("check_map [%d] - offset [%d]\n", ret, i); setbit_map(&map, i-1); // set a higher prio bit, attend to get i-1 here ret = check_map(map); printf("check_map [%d] - offset [%d]\n", ret, i-1); clrbit_map(&map, i-1); // clr the higher prio bit, attend to get i here ret = check_map(map); printf("check_map [%d] - offset [%d]\n", ret, i-1+1); #else // scheduling ret = check_map(map); // printf("<-map -> queue [%d]\n", ret); printf("\t\t\t\t\t\tqueue [%d]\n", ret); // if !(0<=ret<=15), there is no task in the queue, end. if (ret < 0 || ret > 15) { goto label_after_check_list; } //printf("pop\n"); p = list_pop(run_queues->arrays->queue[ret].list); //the "STATE" need to change //save context and post_synch enven // to make clear, I use a "p" here, which should be sch_process_current sch_process_current = p; tmp_sch_process = sch_process_current; //printf("posting the [%s] ...\n", p->old->name); process_post_synch(p->old, PROCESS_EVENT_POLL, NULL); //printf("posted state[%d]\n", p->add->state); sch_process_current = tmp_sch_process; /* * update map * TODO: * pushing back means the only the highest prio process can be called * so it needs the timeslice. */ if (p->add->state == SCH_PROCESS_STATE_RUNNING) { // if the posted process(stroed in p) is still running // we put it back to the list list_add(run_queues->arrays[0].queue[p->add->prio].list, sch_process_current); } else { p = list_head(run_queues->arrays->queue[ret].list); if (p == NULL) { // if not running, and the queue[ret] is empty // we clear the "ret"-th bit in map printf("\t\t\t\t\t\tqueue[%2d] is empty now!\n", ret); clrbit_map(pmap, ret); } } label_after_check_list: while (0) { //do nothing here } process_poll(process_current); #endif }
/*---------------------------------------------------------------------------*/ void etimer_request_poll(void) { process_poll(&etimer_process); }
/*---------------------------------------------------------------------------*/ static void pollhandler(void) { #if !FALLBACK_HAS_ETHERNET_HEADERS //native br is fallback only process_poll(&wpcap_process); uip_len = wpcap_poll(); if(uip_len > 0) { #if NETSTACK_CONF_WITH_IPV6 if(BUF->type == uip_htons(UIP_ETHTYPE_IPV6)) { // printf("wpcap poll calls tcpip"); tcpip_input(); } else #endif /* NETSTACK_CONF_WITH_IPV6 */ if(BUF->type == uip_htons(UIP_ETHTYPE_IP)) { uip_len -= sizeof(struct uip_eth_hdr); tcpip_input(); #if !NETSTACK_CONF_WITH_IPV6 } else if(BUF->type == uip_htons(UIP_ETHTYPE_ARP)) { uip_arp_arpin(); //math /* If the above function invocation resulted in data that should be sent out on the network, the global variable uip_len is set to a value > 0. */ if(uip_len > 0) { wpcap_send(); } #endif /* !NETSTACK_CONF_WITH_IPV6 */ } else { uip_clear_buf(); } } #endif #ifdef UIP_FALLBACK_INTERFACE process_poll(&wpcap_process); uip_len = wfall_poll(); if(uip_len > 0) { #if FALLBACK_HAS_ETHERNET_HEADERS if(BUF->type == uip_htons(UIP_ETHTYPE_IPV6)) { //remove ethernet header and pass ipv6 packet to stack uip_len-=14; //{int i;printf("\n0000 ");for (i=0;i<uip_len;i++) printf("%02x ",*(unsigned char*)(uip_buf+i));printf("\n");} // memcpy(uip_buf, uip_buf+14, uip_len); memcpy(&uip_buf[UIP_LLH_LEN], uip_buf+14, uip_len); //LLH_LEN is zero for native border router to slip radio // CopyMemory(uip_buf, uip_buf+14, uip_len); //{int i;printf("\n0000 ");for (i=0;i<uip_len;i++) printf("%02x ",*(char*)(uip_buf+i));printf("\n");} tcpip_input(); } else goto bail; #elif NETSTACK_CONF_WITH_IPV6 if(BUF->type == uip_htons(UIP_ETHTYPE_IPV6)) { tcpip_input(); } else goto bail; #endif /* NETSTACK_CONF_WITH_IPV6 */ if(BUF->type == uip_htons(UIP_ETHTYPE_IP)) { uip_len -= sizeof(struct uip_eth_hdr); tcpip_input(); #if !NETSTACK_CONF_WITH_IPV6 } else if(BUF->type == uip_htons(UIP_ETHTYPE_ARP)) { uip_arp_arpin(); //math /* If the above function invocation resulted in data that should be sent out on the network, the global variable uip_len is set to a value > 0. */ if(uip_len > 0) { wfall_send(); } #endif /* !NETSTACK_CONF_WITH_IPV6 */ } else { bail: uip_clear_buf(); } } #endif }
/*---------------------------------------------------------------------------*/ static int cc2420_read(void *buf, unsigned short bufsize) { uint8_t footer[2]; uint8_t len; #if CC2420_CONF_CHECKSUM uint16_t checksum; #endif /* CC2420_CONF_CHECKSUM */ if(!CC2420_FIFOP_IS_1) { return 0; } /* if(!pending) { return 0; }*/ pending = 0; GET_LOCK(); cc2420_packets_read++; getrxbyte(&len); if(len > CC2420_MAX_PACKET_LEN) { /* Oops, we must be out of sync. */ flushrx(); RIMESTATS_ADD(badsynch); RELEASE_LOCK(); return 0; } if(len <= AUX_LEN) { flushrx(); RIMESTATS_ADD(tooshort); RELEASE_LOCK(); return 0; } if(len - AUX_LEN > bufsize) { flushrx(); RIMESTATS_ADD(toolong); RELEASE_LOCK(); return 0; } getrxdata(buf, len - AUX_LEN); #if CC2420_CONF_CHECKSUM getrxdata(&checksum, CHECKSUM_LEN); #endif /* CC2420_CONF_CHECKSUM */ getrxdata(footer, FOOTER_LEN); #if CC2420_CONF_CHECKSUM if(checksum != crc16_data(buf, len - AUX_LEN, 0)) { PRINTF("checksum failed 0x%04x != 0x%04x\n", checksum, crc16_data(buf, len - AUX_LEN, 0)); } if(footer[1] & FOOTER1_CRC_OK && checksum == crc16_data(buf, len - AUX_LEN, 0)) { #else if(footer[1] & FOOTER1_CRC_OK) { #endif /* CC2420_CONF_CHECKSUM */ cc2420_last_rssi = footer[0]; cc2420_last_correlation = footer[1] & FOOTER1_CORRELATION; packetbuf_set_attr(PACKETBUF_ATTR_RSSI, cc2420_last_rssi); packetbuf_set_attr(PACKETBUF_ATTR_LINK_QUALITY, cc2420_last_correlation); RIMESTATS_ADD(llrx); } else { RIMESTATS_ADD(badcrc); len = AUX_LEN; } if(CC2420_FIFOP_IS_1) { if(!CC2420_FIFO_IS_1) { /* Clean up in case of FIFO overflow! This happens for every * full length frame and is signaled by FIFOP = 1 and FIFO = * 0. */ flushrx(); } else { /* Another packet has been received and needs attention. */ process_poll(&cc2420_process); } } RELEASE_LOCK(); if(len < AUX_LEN) { return 0; } return len - AUX_LEN; } /*---------------------------------------------------------------------------*/ void cc2420_set_txpower(uint8_t power) { GET_LOCK(); set_txpower(power); RELEASE_LOCK(); }
/** * The CC1101 interrupt handler: called by the hardware interrupt * handler, which is defined as part of the cc1101-arch interface. */ int cc1101_rx_interrupt(void) { /* NB: This function may be called both from an rx interrupt and from cc1101_process */ uint8_t rxbytes, s; if(radio_on_or_off == OFF) { return 0; } #if DEBUG printf("-"); #endif /* DEBUG */ if(SPI_IS_LOCKED()) { #if DEBUG printf("/%d", spi_locked); #endif /* DEBUG */ process_poll(&cc1101_process); return 1; } LOCK_SPI(); s = state(); if(s == CC1101_STATE_RXFIFO_OVERFLOW) { burst_read(CC1101_RXBYTES, &rxbytes, 1); #if DEBUG printf("irqflush\n"); printf("rxbytes 0x%02x\n", rxbytes); #endif /* DEBUG */ flushrx(); RELEASE_SPI(); return 0; } if(s == CC1101_STATE_TXFIFO_UNDERFLOW) { #if DEBUG printf("irqflushtx\n"); #endif /* DEBUG */ strobe(CC1101_SFTX); strobe(CC1101_SRX); RELEASE_SPI(); return 0; } if(is_receiving() && timer_expired(&rxstate.timer)) { #if DEBUG printf("Packet expired, flushing fifo\n"); #endif /* DEBUG */ flushrx(); RELEASE_SPI(); return 0; } #define RX_OVERFLOW 0x80 /* Read each byte from the RXFIFO and put it into the input_byte() function, which takes care of the reception logic. */ do { uint8_t byte; int i, numbytes; rxbytes = read_rxbytes(); if(rxbytes & RX_OVERFLOW) { #if DEBUG printf("ovf\n"); leds_off(LEDS_GREEN;) #endif /* DEBUG */ flushrx(); process_poll(&cc1101_process); RELEASE_SPI(); return 1; }
/* * Interrupt either leaves frame intact in FIFO or reads *only* the * MAC header and sets rx_fifo_remaining_bytes. * * In order to quickly empty the FIFO ack processing is done at * interrupt priority rather than poll priority. */ int __cc2420_intr(void) { u8_t length; const u8_t *const ack_footer = (u8_t *)&h.dst_pan; CLEAR_FIFOP_INT(); if (spi_busy || rx_fifo_remaining_bytes > 0) { /* SPI bus hardware is currently used elsewhere (UART0 or I2C bus) * or we already have a packet in the works and will have to defer * interrupt processing of this packet in a fake interrupt. */ process_poll(&cc2420_process); return 1; } FASTSPI_READ_FIFO_BYTE(length); if (length > MAX_PACKET_LEN) { /* Oops, we must be out of sync. */ FASTSPI_STROBE(CC2420_SFLUSHRX); FASTSPI_STROBE(CC2420_SFLUSHRX); return 0; } h.len = length; if (length < ACK_PACKET_LEN) { FASTSPI_READ_FIFO_GARBAGE(length); /* Rubbish */ return 0; } FASTSPI_READ_FIFO_NO_WAIT(&h.fc0, 5); /* fc0, fc1, seq, dst_pan */ /* Is this an ACK packet? */ if (length == ACK_PACKET_LEN && (h.fc0 & FC0_TYPE_MASK) == FC0_TYPE_ACK) { if (ack_footer[1] & FOOTER1_CRC_OK) { if (h.seq == last_used_seq) { /* Matching ACK number? */ cc2420_ack_received = 1; process_poll(&cc2420_retransmit_process); #if 0 cc2420_last_rssi = ack_footer[0]; cc2420_last_correlation = ack_footer[1] & FOOTER1_CORRELATION; #endif } } return 1; } if (length < (MAC_HDR_LEN + 2)) { FASTSPI_READ_FIFO_GARBAGE(length - 5); return 0; } FASTSPI_READ_FIFO_NO_WAIT(&h.dst, 4); /* dst and src */ /* The payload and footer is now left in the RX FIFO and will be * picked up asynchronously at poll priority in the cc2420_process * below. */ rx_fifo_remaining_bytes = length - MAC_HDR_LEN; process_poll(&cc2420_process); return 1; }
PROCESS_THREAD(spiProcess, ev, data) { PROCESS_BEGIN(); uint8_t spi_data_fifo[SPIFIFOSIZE]; uint8_t packetLen; spi_packet_t spi_rx_pkt; uint8_t* dma_src_end_addr; static uint8_t spi_data_ptr = 0; uint8_t proc_idx; while (1){ PROCESS_YIELD(); switch (spiState){ case SPI_RESET: spi_cs_int = 0; spi_rxfifo_halffull = 0; spiInUse = 0; spi_data_ptr = 0; spix_interrupt_enable(SPIDEV, SSI_IM_RXIM_M); spiState = SPI_WAIT; process_poll(&mainProcess); #ifdef LED_DEBUG leds_off(LEDS_RED); leds_on(LEDS_GREEN); leds_on(LEDS_BLUE); #endif break; /* Wait SPI from Edison*/ case SPI_WAIT: #ifdef LED_DEBUG leds_on(LEDS_BLUE); #endif if (spi_rxfifo_halffull==1){ spi_rxfifo_halffull = 0; spi_data_ptr += spix_get_data(SPIDEV, spi_data_fifo+spi_data_ptr); spix_interrupt_enable(SPIDEV, SSI_IM_RXIM_M); spiInUse = 1; } if (spi_cs_int==1){ spi_data_ptr += spix_get_data(SPIDEV, spi_data_fifo+spi_data_ptr); spi_cs_int = 0; spiInUse = 1; proc_idx = 0; while (proc_idx < spi_data_ptr){ proc_idx += spi_packet_parse(&spi_rx_pkt, spi_data_fifo+proc_idx); switch (spi_rx_pkt.cmd){ // write length and data into tx fifo case SPI_MASTER_REQ_DATA: packetLen = triumviRXPackets[triumviFullIDX].length; spix_put_data_single(SPIDEV, packetLen); dma_src_end_addr = triumviRXPackets[triumviFullIDX].payload + packetLen - 1; udma_set_channel_src(CC2538_SPI0_TX_DMA_CHAN, (uint32_t)(dma_src_end_addr)); udma_set_channel_control_word(CC2538_SPI0_TX_DMA_CHAN, (SPI0TX_DMA_FLAG | udma_xfer_size(packetLen))); udma_channel_enable(CC2538_SPI0_TX_DMA_CHAN); GPIO_CLR_PIN(TRIUMVI_DATA_READY_PORT_BASE, TRIUMVI_DATA_READY_MASK); break; // do nothing... case SPI_MASTER_DUMMY: break; // spi transmission is completed, advances pointer case SPI_MASTER_GET_DATA: if ((triumviAvailIDX!=triumviFullIDX) || (triumviRXBufFull==1)){ triumviRXBufFull = 0; if (triumviFullIDX == TRIUMVI_PACKET_BUF_LEN-1) triumviFullIDX = 0; else triumviFullIDX += 1; #ifndef LED_DEBUG leds_off(LEDS_GREEN); #endif } resetCnt = 0; spiInUse = 0; break; case SPI_MASTER_RADIO_ON: NETSTACK_RADIO.on(); spiInUse = 0; break; case SPI_MASTER_RADIO_OFF: NETSTACK_RADIO.off(); spiInUse = 0; break; default: spiInUse = 0; break; } } spi_data_ptr = 0; #ifndef LED_DEBUG leds_off(LEDS_BLUE); #else leds_on(LEDS_RED); leds_off(LEDS_GREEN); leds_on(LEDS_BLUE); #endif } process_poll(&mainProcess); break; default: break; } } PROCESS_END(); }
/*---------------------------------------------------------------------------*/ void native_rdc_reset_slip(void) { process_poll(&native_rdc_process); }
void rf_rx_handler(){ process_poll(&decryptProcess); }
void drvr_set_status(U8 status) { dcb.status = status; dcb.status_avail = true; process_poll(&drvr_process); }
static void spiFIFOcallBack(){ spix_interrupt_disable(SPIDEV, SSI_IM_RXIM_M); spi_rxfifo_halffull = 1; process_poll(&spiProcess); }
/*---------------------------------------------------------------------------*/ static void request_sent(struct runicast_conn *c, const rimeaddr_t *to, uint8_t retransmissions) { process_poll(&shell_download_process); }
/** * \brief RF212 radio process poll function, to be called from the * interrupt handler to poll the radio process * \retval 0 success */ int rf212_interrupt_poll(void) { volatile uint8_t irq_source; irq_source = trx_reg_read(RF212_REG_IRQ_STATUS); if(irq_source & IRQ_TRX_DONE) { if(flag_transmit==1) { flag_transmit=0; interrupt_callback_in_progress = 0; #if NULLRDC_CONF_802154_AUTOACK_HW //printf("Status %x",trx_reg_read(RF233_REG_TRX_STATE) & TRX_STATE_TRAC_STATUS); if(!(trx_reg_read(RF212_REG_TRX_STATE) & TRX_STATE_TRAC_STATUS)) ack_status = 1; RF212_COMMAND(TRXCMD_RX_AACK_ON); #endif return 0; } if(interrupt_callback_in_progress) { /* we cannot read out info from radio now, return here later (through a poll) */ interrupt_callback_wants_poll = 1; process_poll(&rf212_radio_process); PRINTF("RF212: irq but busy, returns later.\n"); return 0; } interrupt_callback_wants_poll = 0; interrupt_callback_in_progress = 1; /* we have started receiving a frame, len can be read */ pending_frame = 1; process_poll(&rf212_radio_process); } #if 0 /* Note, these are not currently in use but here for completeness. */ if(irq_source & IRQ_TRX_DONE) { /* End of transmitted or received frame. */ } if(irq_source & IRQ_TRXBUF_ACCESS_VIOLATION) { /* * Access violation on the shared TX/RX FIFO. Possible causes: * - buffer underrun while transmitting, ie not enough data in FIFO to tx * - reading too fast from FIFO during rx, ie not enough data received yet * - haven't read last rxed frame when next rx starts, but first is possible * to read out, with possible corruption - check FCS * - writing frames larger than 127 B to FIFO (len byte) */ PRINTF("RF212-arch: access violation.\n"); } if(irq_source & IRQ_BAT_LOW) { /* Battery low */ } if(irq_source & IRQ_RX_ADDRESS_MATCH) { /* receiving frame address match */ } if(irq_source & IRQ_CCA_ED_DONE) { /* CCA/ED done */ } if(irq_source & IRQ_PLL_UNLOCK) { /* PLL unlock */ } if(irq_source & IRQ_PLL_LOCK) { /* PLL lock */ } #endif interrupt_callback_in_progress = 0; return 0; }
/*-----------------------------------------------------------------------------------*/ void blocking_request_callback(void *callback_data, void *response) { struct request_state_t *state = (struct request_state_t *) callback_data; state->response = (coap_packet_t*) response; process_poll(state->process); }
/*---------------------------------------------------------------------------*/ static void motion_interrupt_handler(uint8_t port, uint8_t pin) { process_poll(&motion_int_process); }
/*---------------------------------------------------------------------------*/ void akes_delete_on_update_sent(void *ptr, int status, int transmissions) { process_poll(&delete_process); }