我正试图从TSL261 TI的传感器以正确的格式打印出正确的光强度值。 CC2530和contiki都用于此目的。 smartrf05EB和BB也被使用。
客户:
#include "contiki.h"
#include "contiki-lib.h"
#include "contiki-net.h"
#include "contiki-conf.h"
#include "dev/leds.h"
#include <string.h>
#include "dev/leds.h"
#include "dev/button-sensor.h"
#include "debug.h"
#include "adc-sensor.h"
#include "port.h"
#include "cc253x.h"
#include "sfr-bits.h"
#include "lib/sensors.h"
#define DEBUG DEBUG_PRINT
#include "net/uip-debug.h"
#define SEND_INTERVAL 3 * CLOCK_SECOND
#define MAX_PAYLOAD_LEN 40
static uint16_t buf[MAX_PAYLOAD_LEN];
static uint16_t temp_buf[MAX_PAYLOAD_LEN];
static int rv;
uint16_t lv, tv;
static struct sensors_sensor *sensor;
static float sane = 0;
static int dec;
static int frac;
#define LOCAL_CONN_PORT 3001
static struct uip_udp_conn *l_conn;
#if UIP_CONF_ROUTER
#define GLOBAL_CONN_PORT 3002
static struct uip_udp_conn *g_conn;
#endif
/*---------------------------------------------------------------------------*/
//PROCESS(sensors_test_process, "Sensor Test Process");
PROCESS(udp_client_process, "UDP client process");
#if BUTTON_SENSOR_ON
PROCESS_NAME(ping6_process);
AUTOSTART_PROCESSES(&udp_client_process, &ping6_process);
#else
AUTOSTART_PROCESSES(&udp_client_process);
#endif
/*---------------------------------------------------------------------------*/
static void
tcpip_handler(void)
{
leds_on(LEDS_GREEN);
if(uip_newdata()) {
putstring("0x");
puthex(uip_datalen());
putstring(" bytes response=0x");
puthex((*(uint16_t *) uip_appdata) >> 8);
puthex((*(uint16_t *) uip_appdata) & 0xFF);
putchar('\n');
}
leds_off(LEDS_GREEN);
return;
}
/*---------------------------------------------------------------------------*/
static void ReadLightSensor(void)
{
P0SEL &= ~0x10; /* Set pin as GPIO */
P0DIR &= ~0x10; /* Set pin as input*/
P0INP |= 0x10; /* Set as tri-state*/
APCFG |= 0x10; /* configure ADC on pin*/
ADCCON3 = 0x34; /*This represents the paramters passed into ADCCON3*/
while (!ADCIF);
ADCIF = 0;
tv = ADCL;
lv = ADCH;
// tv |= (((unsigned short) ADCH) << 8);
// tv >>= 4 ;
// lv = tv;
//PRINTF("Port 0 Pin 4 reading = 0x%04x\n\r", lv);
PRINTF("ADCL = 0x%04x\n\r", tv);
PRINTF(" ADCH = 0x%04x\n\r",lv);
return;
}
/*---------------------------------------------------------------------------*/
static void
timeout_handler(void)
{
static int seq_id;
struct uip_udp_conn *this_conn;
leds_on(LEDS_RED);
memset(buf, 0, MAX_PAYLOAD_LEN);
seq_id++;
this_conn = g_conn;
if(uip_ds6_get_global(ADDR_PREFERRED) == NULL) // Only use one port to send
{
return;
}
PRINTF("Client to: ");
PRINT6ADDR(&this_conn->ripaddr);
temp_buf[0] = dec;
temp_buf[1] = frac;
temp_buf[2] = lv;
temp_buf[3] = tv;
//add light values and barometer values
memcpy(buf, temp_buf, sizeof(temp_buf)); //copy data in temp_buf into buf
PRINTF(" Remote Port %u,", UIP_HTONS(this_conn->rport));
PRINTF("\n\r (msg=0x%04x), %u bytes\n", *(uint16_t *) buf, sizeof(buf));
uip_udp_packet_send(this_conn, buf, sizeof(buf));
PRINTF("Decimal = %d ", buf[0]);
PRINTF("Fraction = %d ", buf[1]);
leds_off(LEDS_RED);
}
/*---------------------------------------------------------------------------*/
PROCESS_THREAD(udp_client_process, ev, data)
{
static struct etimer et;
uip_ipaddr_t ipaddr;
PROCESS_BEGIN();
PRINTF("UDP client process started\n");
uip_ip6addr(&ipaddr, 0xfe80, 0, 0, 0, 0x0212, 0x4B00, 0x0205, 0xF37A); //local ipv6 addr
//uip_ip6addr(&ipaddr, 0xfe80, 0, 0, 0, 0x0215, 0x2000, 0x0002, 0x2145);
/* new connection with remote host */
l_conn = udp_new(&ipaddr, UIP_HTONS(3000), NULL);
if(!l_conn) {
PRINTF("udp_new l_conn error.\n");
}
udp_bind(l_conn, UIP_HTONS(LOCAL_CONN_PORT));
PRINTF("Link-Local connection with ");
PRINT6ADDR(&l_conn->ripaddr);
PRINTF(" local/remote port %u/%u\n",
UIP_HTONS(l_conn->lport), UIP_HTONS(l_conn->rport));
uip_ip6addr(&ipaddr, 0xaaaa, 0, 0, 0, 0x0212, 0x4B00, 0x0205, 0xF37A); //global ipv6 addr
//uip_ip6addr(&ipaddr, 0xaaaa, 0, 0, 0, 0x0215, 0x2000, 0x0002, 0x2145);
g_conn = udp_new(&ipaddr, UIP_HTONS(3000), NULL);
if(!g_conn) {
PRINTF("udp_new g_conn error.\n");
}
udp_bind(g_conn, UIP_HTONS(GLOBAL_CONN_PORT));
PRINTF("Global connection with ");
PRINT6ADDR(&g_conn->ripaddr);
PRINTF(" local/remote port %u/%u\n",
UIP_HTONS(g_conn->lport), UIP_HTONS(g_conn->rport));
etimer_set(&et, SEND_INTERVAL);
while(1) {
PROCESS_YIELD();
if(etimer_expired(&et))
{
ReadLightSensor(); // fire function to read from light sensor
sensor = sensors_find(ADC_SENSOR);
if(sensor) {
PRINTF("------------------\n");
leds_on(LEDS_RED);
rv = sensor->value(ADC_SENSOR_TYPE_TEMP);
if(rv != -1) {
sane = 25 + ((rv - 1480) / 4.5);
dec = sane;
frac = (int)(100*(sane - dec));
PRINTF(" Temperature = %d.%02u C (%d)\n", dec, (unsigned int)(frac*100), rv);
}
timeout_handler();
etimer_restart(&et);
} else if(ev == tcpip_event) {
tcpip_handler();
}
}
}
PROCESS_END();
}
服务器:
#include "contiki.h"
#include "contiki-lib.h"
#include "contiki-net.h"
#include <string.h>
#define DEBUG DEBUG_PRINT
#include "net/uip-debug.h"
#include "dev/watchdog.h"
#include "dev/leds.h"
#include "net/rpl/rpl.h"
#include "dev/button-sensor.h"
#include "debug.h"
#define UIP_IP_BUF ((struct uip_ip_hdr *)&uip_buf[UIP_LLH_LEN])
#define UIP_UDP_BUF ((struct uip_udp_hdr *)&uip_buf[uip_l2_l3_hdr_len])
#define MAX_PAYLOAD_LEN 120
#define TABLE_LEN 5
void update_table(float tmpr, uint16_t lv);
void display_vtable();
static struct uip_udp_conn *server_conn;
static uint16_t buf[MAX_PAYLOAD_LEN];
static uint16_t len, lv,tv;
static numofcl = 0;
static float recvtemp;
// structure to hold ip and state
typedef struct {
uip_ipaddr_t IP;
uint8_t nstatus;
uint8_t is_default;
float temp;
uint16_t light;
}verify;
static verify vtable[TABLE_LEN];
#define SERVER_REPLY 1
/* Should we act as RPL root? */
#define SERVER_RPL_ROOT 1
#if SERVER_RPL_ROOT
static uip_ipaddr_t ipaddr;
#endif
/*---------------------------------------------------------------------------*/
PROCESS(udp_server_process, "UDP server process");
AUTOSTART_PROCESSES(&udp_server_process);
/*---------------------------------------------------------------------------*/
static void
tcpip_handler(void)
{
int i,x ;
float g, sumtemp, avgtemp ; //For handling temperature float value
memset(buf, 0, MAX_PAYLOAD_LEN); // set buffer
if(uip_newdata()) {
leds_on(LEDS_RED);
len = uip_datalen();
PRINTF("Incoming packet of length %d\r\n", len);
memcpy(buf, uip_appdata, len);
for (i=0; i<4; i++)
{
PRINTF("0x%04x ",buf[i]);
}
PRINTF("\n\r");
g = (float)buf[1] / 100;
recvtemp = buf[0] + g;
lv = buf[2];
tv = buf[3];
printf("upper light value = 0x%04x\n\r", lv); //print light value in correct format
printf("lower light value= 0x%04x\n\r", tv);
printf("temperature value = %02f\n\r", recvtemp);
// PRINTF("%u\n\r bytes from [", len);
// PRINT6ADDR(&UIP_IP_BUF->srcipaddr);
// PRINTF("]:%u\n", UIP_HTONS(UIP_UDP_BUF->srcport));
update_table(recvtemp,lv);
PRINTF("\n\rnumofcl = %d\n\r", numofcl);
// Table Full condition
if ( numofcl == TABLE_LEN )
{
PRINTF("\n\rTable Full\n");
//Calculate average
sumtemp = 0;
for(i = 0; i < TABLE_LEN; i++)
{
sumtemp += vtable[i].temp;
}
avgtemp = sumtemp / TABLE_LEN;
PRINTF("\n\rAverage Temperature = %d\n", avgtemp);
//clear sensor data ..temp,light,etc
for (x=0; x<TABLE_LEN; x++)
{
//vtable[x].nstatus = 0;
vtable[x].temp = 0;
vtable[x].light = 0;
}
}
#if SERVER_REPLY
uip_ipaddr_copy(&server_conn->ripaddr, &UIP_IP_BUF->srcipaddr);
server_conn->rport = UIP_UDP_BUF->srcport;
uip_udp_packet_send(server_conn, buf, len);
/* Restore server connection to allow data from any node */
uip_create_unspecified(&server_conn->ripaddr);
server_conn->rport = 0;
#endif
}
leds_off(LEDS_RED);
display_vtable();
return;
}
/*---------------------------------------------------------------------------*/
#if (BUTTON_SENSOR_ON && (DEBUG==DEBUG_PRINT))
static void
print_stats()
{
PRINTF("tl=%lu, ts=%lu, bs=%lu, bc=%lu\n",
rimestats.toolong, rimestats.tooshort, rimestats.badsynch,
rimestats.badcrc);
PRINTF("llrx=%lu, lltx=%lu, rx=%lu, tx=%lu\n", rimestats.llrx,
rimestats.lltx, rimestats.rx, rimestats.tx);
}
#endif
/*---------------------------------------------------------------------------*/
static void
print_local_addresses(void)
{
int i;
uint8_t state;
PRINTF("Server IPv6 addresses:\n");
for(i = 0; i < UIP_DS6_ADDR_NB; i++) {
state = uip_ds6_if.addr_list[i].state;
if(uip_ds6_if.addr_list[i].isused && (state == ADDR_TENTATIVE || state
== ADDR_PREFERRED)) {
PRINTF(" ");
PRINT6ADDR(&uip_ds6_if.addr_list[i].ipaddr);
PRINTF("\n");
if(state == ADDR_TENTATIVE) {
uip_ds6_if.addr_list[i].state = ADDR_PREFERRED;
}
}
}
}
/*---------------------------------------uip_newdata------------------------------------*/
#if SERVER_RPL_ROOT
void
create_dag()
{
rpl_dag_t *dag;
uip_ip6addr(&ipaddr, 0xaaaa, 0, 0, 0, 0, 0, 0, 0);
uip_ds6_set_addr_iid(&ipaddr, &uip_lladdr);
uip_ds6_addr_add(&ipaddr, 0, ADDR_AUTOCONF);
print_local_addresses();
dag = rpl_set_root(RPL_DEFAULT_INSTANCE,
&uip_ds6_get_global(ADDR_PREFERRED)->ipaddr);
if(dag != NULL) {
uip_ip6addr(&ipaddr, 0xaaaa, 0, 0, 0, 0, 0, 0, 0);
rpl_set_prefix(dag, &ipaddr, 64);
PRINTF("Created a new RPL dag with ID: ");
PRINT6ADDR(&dag->dag_id);
PRINTF("\n");
}
}
#endif /* SERVER_RPL_ROOT */
void update_table(float tmpr, uint16_t lv)
{
int x;
uint8_t intbl = 0;
uip_ipaddr_t defaultIP;
uip_ipaddr(&defaultIP,0,0,0,0);
for (x=0; x<TABLE_LEN; x++)
{
if(uip_ipaddr_cmp(&vtable[x].IP, &UIP_IP_BUF->srcipaddr)) //compare ip's / updating an existing client
{
//if (vtable[x].nstatus == 0)
//{
//vtable[x].nstatus = 1;
vtable[x].temp = tmpr;
vtable[x].light = lv;
//}
PRINTF("Existing field updated");
break;
}
else if(vtable[x].is_default == 0) // updating a null field/ adding new client
{
uip_ipaddr_copy(&vtable[x].IP, &UIP_IP_BUF->srcipaddr); //
//vtable[x].nstatus = 1;
vtable[x].is_default = 1;
vtable[x].temp = tmpr;
vtable[x].light = lv;
PRINTF("new field updated");
numofcl++;
break;
}
}
}
void
display_vtable()
{
int j;
for(j = 0; j < TABLE_LEN; j++)
{
PRINTF("\n\rvtable[%d] --> uip_addr =",j);
uip_debug_ipaddr_print(&vtable[j].IP);
PRINTF( "status = %d\r\n", vtable[j].nstatus);
PRINTF( "temperature = %02f\n", vtable[j].temp );
PRINTF(" Light = 0x%04x\n\r", vtable[j].light);
PRINTF( "is_default = %d\n\r", vtable[j].is_default);
}
}
/*---------------------------------------------------------------------------*/
PROCESS_THREAD(udp_server_process, ev, data)
{
uint8_t i;
PROCESS_BEGIN();
for(i = 0; i < TABLE_LEN; i++) //Initialize table by setting values to zero
{
uip_ipaddr(&vtable[i].IP,0,0,0,0);
vtable[i].nstatus = 0;
vtable[i].is_default = 0;
}
putstring("Starting UDP server\n");
#if BUTTON_SENSOR_ON
putstring("Button 1: Print RIME stats\n");
#endif
#if SERVER_RPL_ROOT
create_dag();
#endif
server_conn = udp_new(NULL, UIP_HTONS(0), NULL);
udp_bind(server_conn, UIP_HTONS(3000));
PRINTF("Listen port: 3000, TTL=%u\n", server_conn->ttl);
while(1) {
PROCESS_YIELD();
if(ev == tcpip_event) {
tcpip_handler();
#if (BUTTON_SENSOR_ON && (DEBUG==DEBUG_PRINT))
} else if(ev == sensors_event && data == &button_sensor) {
print_stats();
#endif /* BUTTON_SENSOR_ON */
}
}
PROCESS_END();
}
/*---------------------------------------------------------------------------*/
服务器收到的值看起来不正确。 记录的最高值(最亮)是0x07FF,而记录的最低值(最亮)是0x0FFE。我不知道我的代码或微控制器是否有问题,我期待数字接近于零(以十六进制形式)表示最暗,而值接近“0xFFFF”表示最亮的值。有什么帮助吗?