Commit 529b4a4a authored by Alessandro Rubini's avatar Alessandro Rubini

Merge branch 'temperature-framework'

parents 3e630d08 c58702a0
......@@ -26,6 +26,10 @@ config RAMSIZE
default 65536 if WR_SWITCH
default 131072
config TEMP_POLL_INTERVAL
int
default 15
config PLL_VERBOSE
boolean
default y if WR_SWITCH
......@@ -188,6 +192,10 @@ config PRINT_BUFSIZE
also constraints the maximum lenght of text that can be written
in a single call to printf.
config TEMP_POLL_INTERVAL
depends on DEVELOPER && WR_NODE
int "Poll interval, in seconds, for temperature sensors"
config CMD_LL
depends on DEVELOPER && WR_NODE
bool "Build low-level commands for development/testing"
......@@ -324,6 +332,13 @@ config WRC_VERBOSE
help
This enables some more diagnostic messages. Normally off.
config FAKE_TEMPERATURES
depends on DEVELOPER
boolean "Offer an array of 3 fake temperatures, for testing"
help
The option adds also a "faketemp" command, used to set
the fake temperatures: e.g. "faketemp 120 -10 50"
config VLAN
depends on DEVELOPER
boolean "Filter and rx/tx frames in a VLAN (as opposed to untagged)"
......
......@@ -10,4 +10,9 @@ SECTIONS
KEEP(*(.cmd))
__cmd_end = .;
}
.temp : {
__temp_begin = .;
KEEP(*(.temp))
__temp_end = .;
}
}
......@@ -2,6 +2,7 @@ obj-$(CONFIG_WR_NODE) += \
dev/endpoint.o \
dev/ep_pfilter.o \
dev/i2c.o \
dev/temperature.o \
dev/minic.o \
dev/pps_gen.o \
dev/syscon.o \
......@@ -17,9 +18,12 @@ obj-$(CONFIG_SDB_STORAGE) += dev/sdb-storage.o
obj-$(CONFIG_W1) += dev/w1.o dev/w1-hw.o dev/w1-shell.o
obj-$(CONFIG_W1) += dev/w1-temp.o dev/w1-eeprom.o
obj-$(CONFIG_W1) += dev/temp-w1.o
obj-$(CONFIG_UART) += dev/uart.o
obj-$(CONFIG_UART_SW) += dev/uart-sw.o
obj-$(CONFIG_FAKE_TEMPERATURES) += dev/fake-temp.o
# Filter rules are selected according to configuration, but we may
# have more than one. Note: the filename is reflected in symbol names,
# so they are hardwired in ../Makefile (and ../tools/pfilter-builder too)
......
/*
* This work is part of the White Rabbit project
*
* Copyright (C) 2016 GSI (www.gsi.de)
* Author: Alessandro rubini
*
* Released according to the GNU GPL, version 2 or any later version.
*/
#include <wrc.h>
#include <temperature.h>
#include <shell.h>
static struct wrc_onetemp temp_fake_data[] = {
{"roof", TEMP_INVALID},
{"core", TEMP_INVALID},
{"case", TEMP_INVALID},
{NULL,}
};
static int temp_fake_refresh(struct wrc_temp *t)
{
/* nothing to do */
return 0;
}
/* not static at this point, because it's the only one */
DEFINE_TEMPERATURE(w1) = {
.read = temp_fake_refresh,
.t = temp_fake_data,
};
static int cmd_faketemp(const char *args[])
{
int i;
const char *dot;
if (!args[0]) {
pp_printf("%08x %08x %08x\n", temp_fake_data[0].t,
temp_fake_data[1].t, temp_fake_data[2].t);
return 0;
}
for (i = 0; i < 3 && args[i]; i++) {
int sign = 1, val;
/* accept negative, and at most one decimal */
if (args[i][0] == '-')
sign = -1, args[i]++;
dot = fromdec(args[i], &val);
val <<= 16;
if (dot[0] == '.' && dot[1] >= '0' && dot[1] <= '9')
val += 0x10000 / 10 * (dot[1] - '0');
temp_fake_data[i].t = val * sign;
}
return 0;
}
DEFINE_WRC_COMMAND(faketemp) = {
.name = "faketemp",
.exec = cmd_faketemp,
};
/*
* This work is part of the White Rabbit project
*
* Copyright (C) 2016 GSI (www.gsi.de)
* Author: Alessandro rubini
*
* Released according to the GNU GPL, version 2 or any later version.
*/
#include <wrc.h>
#include <w1.h>
#include <temperature.h>
static struct wrc_onetemp temp_w1_data[] = {
{"pcb", TEMP_INVALID},
{NULL,}
};
static unsigned long nextt;
static int niterations;
/* Returns 1 if it did something */
static int temp_w1_refresh(struct wrc_temp *t)
{
static int done;
if (!done) {
nextt = timer_get_tics() + 1000;
done++;
}
/* Odd iterations: send the command, even iterations: read back */
int phase = niterations & 1;
static int intervals[] = {
200, (1000 * CONFIG_TEMP_POLL_INTERVAL) - 200
};
if (time_before(timer_get_tics(), nextt))
return 0;
nextt += intervals[phase];
niterations++;
switch(phase) {
case 0:
w1_read_temp_bus(&wrpc_w1_bus, W1_FLAG_NOWAIT);
break;
case 1:
temp_w1_data[0].t =
w1_read_temp_bus(&wrpc_w1_bus, W1_FLAG_COLLECT);
break;
}
return 1;
}
/* not static at this point, because it's the only one */
DEFINE_TEMPERATURE(w1) = {
.read = temp_w1_refresh,
.t = temp_w1_data,
};
/*
* This work is part of the White Rabbit project
*
* Copyright (C) 2016 GSI (www.gsi.de)
* Author: Alessandro rubini
*
* Released according to the GNU GPL, version 2 or any later version.
*/
#include <wrc.h>
#include <string.h>
#include <temperature.h>
#include <shell.h>
extern struct wrc_temp __temp_begin[], __temp_end[];
/*
* Library functions
*/
uint32_t wrc_temp_get(char *name)
{
struct wrc_temp *ta;
struct wrc_onetemp *wt;
for (ta = __temp_begin; ta < __temp_end; ta++)
for (wt = ta->t; wt->name; wt++) {
if (!strcmp(wt->name, name))
return wt->t;
}
return TEMP_INVALID;
}
struct wrc_onetemp *wrc_temp_getnext(struct wrc_onetemp *pt)
{
struct wrc_temp *ta;
struct wrc_onetemp *wt;
if (!pt) { /* first one */
if (__temp_begin != __temp_end)
return __temp_begin->t;
}
if (pt[1].name)
return pt + 1;
/* get next array, if any */
for (ta = __temp_begin; ta < __temp_end; ta++) {
for (wt = ta->t; wt->name; wt++) {
if (wt == pt) {
ta++;
if (ta >= __temp_end)
return NULL;
return ta->t;
}
}
}
return NULL;
}
extern int wrc_temp_format(char *buffer, int len)
{
struct wrc_onetemp *p;
int l = 0, i = 0;
int32_t t;
for (p = wrc_temp_getnext(NULL); p; p = wrc_temp_getnext(p), i++) {
if (l + 16 > len) {
l += sprintf(buffer + l, " ENOSPC");
return l;
}
t = p->t;
l += sprintf(buffer + l, "%s%s:", i ? " " : "", p->name);
if (t == TEMP_INVALID) {
l += sprintf(buffer + l, "INVALID");
continue;
}
if (t < 0) {
t = -(signed)t;
l += sprintf(buffer + l, "-");
}
l += sprintf(buffer + l,"%d.%04d", t >> 16,
((t & 0xffff) * 10 * 1000 >> 16));
}
return l;
}
/*
* The task
*/
void wrc_temp_init(void)
{
struct wrc_temp *ta;
/* Call all actors, so they can init themselves (using ->data) */
for (ta = __temp_begin; ta < __temp_end; ta++)
ta->read(ta);
}
int wrc_temp_refresh(void)
{
struct wrc_temp *ta;
int ret = 0;
for (ta = __temp_begin; ta < __temp_end; ta++)
ret += ta->read(ta);
return (ret > 0);
}
/*
* The shell command
*/
static int cmd_temp(const char *args[])
{
char buffer[80];
wrc_temp_format(buffer, sizeof(buffer));
pp_printf("%s\n", buffer);
return 0;
}
DEFINE_WRC_COMMAND(temp) = {
.name = "temp",
.exec = cmd_temp,
};
/*
* This work is part of the White Rabbit project
*
* Copyright (C) 2016 GSI (www.gsi.de)
* Author: Alessandro rubini
*
* Released according to the GNU GPL, version 2 or any later version.
*/
#ifndef __TEMPERATURE_H__
#define __TEMPERATURE_H__
struct wrc_onetemp {
char *name;
int32_t t; /* fixed point, 16.16 (signed!) */
};
#define TEMP_INVALID (0x8000 << 16)
struct wrc_temp {
int (*read)(struct wrc_temp *);
void *data;
struct wrc_onetemp *t; /* zero-terminated */
};
#define DEFINE_TEMPERATURE(_name) \
static struct wrc_temp __wrc_temp_ ## _name \
__attribute__((section(".temp"), __used__))
/* the task */
extern void wrc_temp_init(void);
extern int wrc_temp_refresh(void);
/* lib functions */
extern uint32_t wrc_temp_get(char *name);
struct wrc_onetemp *wrc_temp_getnext(struct wrc_onetemp *);
extern int wrc_temp_format(char *buffer, int len);
#endif /* __TEMPERATURE_H__ */
......@@ -18,6 +18,7 @@
#include <syscon.h>
#include <pps_gen.h>
#include <onewire.h>
#include <temperature.h>
#include "wrc_ptp.h"
#include "hal_exports.h"
#include "lib/ipv4.h"
......@@ -350,11 +351,7 @@ int wrc_log_stats(void)
if (1) {
int32_t temp;
//first read the value from previous measurement,
//first one will be random, I know
temp = w1_read_temp_bus(&wrpc_w1_bus, W1_FLAG_COLLECT);
//then initiate new conversion for next loop cycle
w1_read_temp_bus(&wrpc_w1_bus, W1_FLAG_NOWAIT);
temp = wrc_temp_get("pcb");
pp_printf("temp: %d.%04d C", temp >> 16,
(int)((temp & 0xffff) * 10 * 1000 >> 16));
}
......
......@@ -14,6 +14,7 @@
#include <wrc.h>
#include <w1.h>
#include <temperature.h>
#include "syscon.h"
#include "uart.h"
#include "endpoint.h"
......@@ -210,6 +211,10 @@ struct wrc_task wrc_tasks[] = {
}, {
.name = "spll-bh",
.job = spll_update,
}, {
.name = "temperature",
.init = wrc_temp_init,
.job = wrc_temp_refresh,
#ifdef CONFIG_IP
}, {
.name = "ipv4",
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment