stash
This commit is contained in:
parent
ce8b71daf0
commit
9c5fb65a90
6 changed files with 390 additions and 30 deletions
13
.build.yml
13
.build.yml
|
@ -25,14 +25,8 @@ steps:
|
|||
commands:
|
||||
- apt update
|
||||
- apt install -y make zip
|
||||
- cd pcb
|
||||
- kibot -d gen -c fiatlux.kiplot.yaml -s update_xml,run_drc -i
|
||||
- kibot -d gen -c fiatlux.kiplot.yaml -s update_xml,run_erc -i
|
||||
- kibot -d gen -c fiatlux.kiplot.yaml -s run_drc,run_erc print_sch
|
||||
- kibot -d gen -c fiatlux.kiplot.yaml -s all print_front gerbers
|
||||
- ls -lA
|
||||
- cd -
|
||||
- make pcb -j$(nproc)
|
||||
- make pcb -j$(nproc) BOARD=fiatlux
|
||||
- make pcb -j$(nproc) BOARD=fiatlux_cc48
|
||||
|
||||
- name: case
|
||||
image: debian:sid
|
||||
|
@ -67,7 +61,8 @@ steps:
|
|||
files:
|
||||
- firmware/firmware/fiatlux.bin
|
||||
- firmware/otaflash.py
|
||||
- pcb/pcb.zip
|
||||
- pcb/fiatlux_pcb.zip
|
||||
- pcb/fiatlux_cc48_pcb.zip
|
||||
checksum:
|
||||
- sha512
|
||||
- md5
|
||||
|
|
|
@ -7,12 +7,12 @@
|
|||
#include <espressif/esp_common.h>
|
||||
|
||||
constexpr unsigned syslog_buffer_size = 1024;
|
||||
char syslog_buf[syslog_buffer_size];
|
||||
char syslog_buf[syslog_buffer_size + 1];
|
||||
volatile unsigned head = 0;
|
||||
volatile unsigned streams = 0;
|
||||
|
||||
extern "C" void syslog(const char *msg) {
|
||||
printf("syslog> %s", msg);
|
||||
//printf("syslog> %s", msg);
|
||||
while (char c = *msg++) {
|
||||
syslog_buf[head++ % syslog_buffer_size] = c;
|
||||
}
|
||||
|
|
308
firmware/lux.cpp
308
firmware/lux.cpp
|
@ -9,24 +9,308 @@
|
|||
#include <task.h>
|
||||
|
||||
#include <esp/spi.h>
|
||||
#include <ws2812_i2s/ws2812_i2s.h>
|
||||
|
||||
const int signal_led_pin = 2;
|
||||
extern "C" {
|
||||
#include <sysparam.h>
|
||||
}
|
||||
|
||||
const int cs0 = 15;
|
||||
const int gpio4 = 4;
|
||||
const int gpio5 = 5;
|
||||
struct apa10xx_pixel_t {
|
||||
struct {
|
||||
unsigned int mod: 5, marker: 3;
|
||||
} __attribute__((packed)) global = {0x1F, 0x7};
|
||||
uint8_t b = 0;
|
||||
uint8_t g = 0;
|
||||
uint8_t r = 0;
|
||||
};
|
||||
|
||||
static ws2812_pixel_t next_colour(int i) {
|
||||
ws2812_pixel_t colour = {{0, 0, 0, 0}};
|
||||
if(i == 8) {
|
||||
colour.white = 32;
|
||||
} else {
|
||||
colour.red = i & 1 ? 32 : 0;
|
||||
colour.green = i & 2 ? 32 : 0;
|
||||
colour.blue = i & 4 ? 32 : 0;
|
||||
}
|
||||
|
||||
return colour;
|
||||
}
|
||||
|
||||
static apa10xx_pixel_t next_color(int i) {
|
||||
apa10xx_pixel_t colour;
|
||||
colour.global.mod = 8;
|
||||
colour.r = i & 1 ? 32 : 0;
|
||||
colour.g = i & 2 ? 32 : 0;
|
||||
colour.b = i & 4 ? 32 : 0;
|
||||
|
||||
return colour;
|
||||
}
|
||||
|
||||
rgba_t top_color;
|
||||
rgba_t bottom_color;
|
||||
|
||||
namespace fiatlux {
|
||||
|
||||
struct hal_error_t {
|
||||
constexpr hal_error_t() = default;
|
||||
|
||||
hal_error_t(const char *) {}
|
||||
|
||||
hal_error_t(const char *, hal_error_t *cause) {}
|
||||
};
|
||||
|
||||
constexpr hal_error_t empty_error;
|
||||
|
||||
enum class hal_module_t {
|
||||
NONE, SIGNAL, RELAIS, SPI_DIMMER, WS28X, APA10X
|
||||
};
|
||||
|
||||
namespace ports {
|
||||
hal_module_t spi = hal_module_t::NONE;
|
||||
hal_module_t uart = hal_module_t::NONE;
|
||||
hal_module_t gpio2 = hal_module_t::NONE;
|
||||
hal_module_t gpio4 = hal_module_t::NONE;
|
||||
hal_module_t gpio5 = hal_module_t::NONE;
|
||||
hal_module_t gpio15 = hal_module_t::NONE;
|
||||
}
|
||||
|
||||
namespace signal {
|
||||
void write_data(bool data) {
|
||||
gpio_write(2, !data);
|
||||
}
|
||||
|
||||
void setup() {
|
||||
gpio_enable(2, GPIO_OUTPUT);
|
||||
}
|
||||
}
|
||||
|
||||
namespace relais {
|
||||
void write_data(bool a, bool b) {
|
||||
gpio_write(4, a);
|
||||
gpio_write(5, b);
|
||||
}
|
||||
|
||||
void write_data(uint8_t data[2]) {
|
||||
write_data((bool) data[0], (bool) data[1]);
|
||||
}
|
||||
|
||||
void setup() {
|
||||
gpio_enable(4, GPIO_OUTPUT);
|
||||
gpio_enable(5, GPIO_OUTPUT);
|
||||
}
|
||||
}
|
||||
|
||||
namespace spi_dimmer {
|
||||
constexpr int cs0 = 15;
|
||||
|
||||
void write_data(uint16_t data[6]) {
|
||||
for (int i = 0; i < 6; ++i) {
|
||||
int dac_val = (data[i] << 2) & 0x3FFC;
|
||||
|
||||
spi_transfer_8(1, ~(0x00));
|
||||
gpio_write(cs0, true);
|
||||
gpio_write(cs0, false);
|
||||
spi_transfer_8(1, ~(0x01 << i));
|
||||
gpio_write(cs0, true);
|
||||
gpio_write(cs0, false);
|
||||
|
||||
spi_transfer_16(1, dac_val);
|
||||
|
||||
spi_transfer_8(1, ~(0x00));
|
||||
gpio_write(cs0, true);
|
||||
gpio_write(cs0, false);
|
||||
spi_transfer_8(1, ~(0x01 << i));
|
||||
gpio_write(cs0, true);
|
||||
gpio_write(cs0, false);
|
||||
}
|
||||
}
|
||||
|
||||
void setup() {
|
||||
gpio_enable(cs0, GPIO_OUTPUT);
|
||||
spi_init(1, SPI_MODE0, SPI_FREQ_DIV_1M, 1, SPI_BIG_ENDIAN, 1);
|
||||
}
|
||||
}
|
||||
|
||||
namespace ws28x {
|
||||
void write_data(ws2812_pixel_t *data) {
|
||||
ws2812_i2s_update(data, PIXEL_RGBW);
|
||||
}
|
||||
|
||||
void setup(size_t len) {
|
||||
ws2812_i2s_init(len, PIXEL_RGBW);
|
||||
}
|
||||
}
|
||||
|
||||
namespace apa10x {
|
||||
void write_data(apa10xx_pixel_t *data, size_t len) {
|
||||
spi_transfer_32(1, 0x00000000);
|
||||
for (size_t i = 0; i < len; i++)
|
||||
spi_transfer_32(1, *(uint32_t *) &data[i]);
|
||||
//spi_transfer_32(1, *(uint32_t *) &data[len - 1]); // dunno maybe this helps
|
||||
//spi_transfer_32(1, *(uint32_t *) &data[len - 1]); // dunno maybe this helps
|
||||
spi_transfer_32(1, 0xFFFFFFFF);
|
||||
spi_transfer_32(1, 0xFFFFFFFF);
|
||||
}
|
||||
|
||||
void setup() {
|
||||
spi_init(1, SPI_MODE0, SPI_FREQ_DIV_1M, 1, SPI_LITTLE_ENDIAN, false);
|
||||
}
|
||||
}
|
||||
|
||||
hal_error_t write_channel(uint8_t *data, size_t count, size_t stride, hal_module_t mod) {
|
||||
if(mod == hal_module_t::SIGNAL) {
|
||||
if(count != 1)
|
||||
return "unsupported value for count";
|
||||
if(stride != 1)
|
||||
return "unsupported value for stride";
|
||||
signal::write_data(data[0]);
|
||||
} else if(mod == hal_module_t::RELAIS) {
|
||||
if(count != 2)
|
||||
return "unsupported value for count";
|
||||
if(stride != 1)
|
||||
return "unsupported value for stride";
|
||||
relais::write_data(data);
|
||||
} else if(mod == hal_module_t::SPI_DIMMER) {
|
||||
if(count != 6)
|
||||
return "unsupported value for count";
|
||||
if(stride != 2)
|
||||
return "unsupported value for stride";
|
||||
spi_dimmer::write_data((uint16_t *) data);
|
||||
} else if(mod == hal_module_t::WS28X) {
|
||||
if(stride != 4)
|
||||
return "unsupported value for stride";
|
||||
ws28x::write_data((ws2812_pixel_t *) data);
|
||||
} else if(mod == hal_module_t::APA10X) {
|
||||
if(stride != 4)
|
||||
return "unsupported value for stride";
|
||||
apa10x::write_data((apa10xx_pixel_t *) data, count);
|
||||
} else {
|
||||
return "unsupported module";
|
||||
}
|
||||
return empty_error;
|
||||
}
|
||||
|
||||
hal_error_t setup_channel(size_t count, size_t stride, hal_module_t mod) {
|
||||
/*if(mod == hal_module_t::SIGNAL) {
|
||||
if(count != 1)
|
||||
return "unsupported value for count";
|
||||
if(stride != 1)
|
||||
return "unsupported value for stride";
|
||||
signal::write_data(data[0]);
|
||||
} else if(mod == hal_module_t::RELAIS) {
|
||||
if(count != 2)
|
||||
return "unsupported value for count";
|
||||
if(stride != 1)
|
||||
return "unsupported value for stride";
|
||||
relais::write_data(data);
|
||||
} else if(mod == hal_module_t::SPI_DIMMER) {
|
||||
if(count != 6)
|
||||
return "unsupported value for count";
|
||||
if(stride != 2)
|
||||
return "unsupported value for stride";
|
||||
spi_dimmer::write_data((uint16_t *) data);
|
||||
} else if(mod == hal_module_t::WS28X) {
|
||||
if(stride != 4)
|
||||
return "unsupported value for stride";
|
||||
ws28x::write_data((ws2812_pixel_t *) data, count);
|
||||
} else if(mod == hal_module_t::APA10X) {
|
||||
if(stride != 4)
|
||||
return "unsupported value for stride";
|
||||
apa10x::write_data((apa10xx_pixel_t *) data, count);
|
||||
} else {
|
||||
return "unsupported module";
|
||||
}*/
|
||||
return empty_error;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//ws2812_pixel_t **pixels_ptr;
|
||||
|
||||
extern "C" void signal_led(bool state) {
|
||||
gpio_write(signal_led_pin, !state);
|
||||
fiatlux::signal::write_data(state);
|
||||
}
|
||||
|
||||
extern "C" void lux_task(void *pvParameters) {
|
||||
|
||||
gpio_enable(signal_led_pin, GPIO_OUTPUT);
|
||||
gpio_enable(cs0, GPIO_OUTPUT);
|
||||
gpio_enable(gpio4, GPIO_OUTPUT);
|
||||
gpio_enable(gpio5, GPIO_OUTPUT);
|
||||
spi_init(1, SPI_MODE0, SPI_FREQ_DIV_1M, 1, SPI_BIG_ENDIAN, 1);
|
||||
/* This task uses the high level GPIO API (esp_gpio.h) to blink an LED.
|
||||
*
|
||||
*/
|
||||
extern "C" [[noreturn]] void lux_task(void *pvParameters) {
|
||||
|
||||
vTaskDelete(nullptr);
|
||||
int32_t lux_ws2812_number = 240;
|
||||
auto ret = sysparam_get_int32("lux_ws2812_number", &lux_ws2812_number);
|
||||
if(ret != SYSPARAM_OK)
|
||||
lux_ws2812_number = 240;
|
||||
|
||||
int32_t lux_apa10xx_number = 40;
|
||||
ret = sysparam_get_int32("lux_apa10xx_number", &lux_apa10xx_number);
|
||||
if(ret != SYSPARAM_OK)
|
||||
lux_apa10xx_number = 40;
|
||||
|
||||
ws2812_pixel_t pixels[lux_ws2812_number];
|
||||
ws2812_i2s_init(lux_ws2812_number, PIXEL_RGBW);
|
||||
memset(pixels, 0, sizeof(ws2812_pixel_t) * lux_ws2812_number);
|
||||
|
||||
apa10xx_pixel_t leds[lux_apa10xx_number];
|
||||
|
||||
//lux_apa102c_number
|
||||
|
||||
//gpio_enable(9, GPIO_INPUT);
|
||||
//gpio_enable(10, GPIO_INPUT);
|
||||
|
||||
//fiatlux::spi_dimmer::setup();
|
||||
|
||||
fiatlux::signal::setup();
|
||||
fiatlux::relais::setup();
|
||||
|
||||
fiatlux::apa10x::setup();
|
||||
|
||||
while (true) {
|
||||
/*for (int j = 0; j < 64; j++) {
|
||||
for (int i = 0; i < 8; i++)
|
||||
spi_dac(i, 64 * j);
|
||||
//printf("> %d\n", 64*j);
|
||||
vTaskDelay(100 / portTICK_PERIOD_MS);
|
||||
}*/
|
||||
/*gpio_write(gpio4, 1);
|
||||
vTaskDelay(200 / portTICK_PERIOD_MS);
|
||||
gpio_write(gpio4, 0);
|
||||
for (int i = 0; i < 8; i++)
|
||||
spi_dac(i, 0);
|
||||
|
||||
gpio_write(gpio5, 1);
|
||||
vTaskDelay(200 / portTICK_PERIOD_MS);
|
||||
gpio_write(gpio5, 0);*/
|
||||
fiatlux::signal::write_data(false);
|
||||
for (int c = 8; c >= 0; c--) {
|
||||
|
||||
/*for (auto &pixel: pixels) {
|
||||
pixel = next_colour(c);
|
||||
}*/
|
||||
|
||||
for (auto &led: leds) {
|
||||
led = next_color(c);
|
||||
}
|
||||
|
||||
for (int i = 0; i < 120; i++)
|
||||
pixels[i] = {{top_color.r, top_color.g, top_color.b, top_color.a}};
|
||||
|
||||
for (int i = 120; i < 240; i++)
|
||||
pixels[i] = {{bottom_color.r, bottom_color.g, bottom_color.b, bottom_color.a}};
|
||||
|
||||
|
||||
ws2812_i2s_update(pixels, PIXEL_RGBW);
|
||||
fiatlux::write_channel((uint8_t *) &leds[0], lux_apa10xx_number, 4, fiatlux::hal_module_t::APA10X);
|
||||
vTaskDelay(200 / portTICK_PERIOD_MS);
|
||||
}
|
||||
fiatlux::relais::write_data(true, false);
|
||||
vTaskDelay(200 / portTICK_PERIOD_MS);
|
||||
fiatlux::relais::write_data(false, true);
|
||||
vTaskDelay(200 / portTICK_PERIOD_MS);
|
||||
fiatlux::relais::write_data(false, false);
|
||||
fiatlux::signal::write_data(true);
|
||||
vTaskDelay(200 / portTICK_PERIOD_MS);
|
||||
|
||||
}
|
||||
}
|
|
@ -13,6 +13,16 @@ void lux_task(void *pvParameters);
|
|||
|
||||
void signal_led(bool state);
|
||||
|
||||
typedef struct {
|
||||
char r;
|
||||
char g;
|
||||
char b;
|
||||
char a;
|
||||
} rgba_t;
|
||||
|
||||
extern rgba_t top_color;
|
||||
extern rgba_t bottom_color;
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -30,6 +30,8 @@ using namespace fiatlux;
|
|||
|
||||
#define vTaskDelayMs(ms) vTaskDelay((ms) / portTICK_PERIOD_MS)
|
||||
|
||||
const char hex_lookup[] = "0123456789ABCDEF\0\0";
|
||||
|
||||
uint16_t voltage_val;
|
||||
|
||||
struct {
|
||||
|
@ -230,6 +232,8 @@ void websocket_task(void *pvParameter) {
|
|||
vTaskDelete(nullptr);
|
||||
}
|
||||
|
||||
char str[] = "L00000000\n";
|
||||
|
||||
/**
|
||||
* This function is called when websocket frame is received.
|
||||
*
|
||||
|
@ -254,6 +258,47 @@ void websocket_cb(struct tcp_pcb *pcb, char *data, u16_t data_len,
|
|||
// Clear Config
|
||||
res.cmd = (messages::id) 'X';
|
||||
res.ret = OK;
|
||||
} else if(data[0] == 'B') {
|
||||
// Disable LED
|
||||
uint32_t val = data[4] | (data[5] << 8) | (data[6] << 16) | (data[7] << 24);
|
||||
bottom_color.r = data[7];
|
||||
bottom_color.g = data[6];
|
||||
bottom_color.b = data[5];
|
||||
str[0] = 'B';
|
||||
str[2] = hex_lookup[val & 0xF];
|
||||
str[1] = hex_lookup[(val >> 4) & 0xF];
|
||||
str[4] = hex_lookup[(val >> 8) & 0xF];
|
||||
str[3] = hex_lookup[(val >> 12) & 0xF];
|
||||
str[6] = hex_lookup[(val >> 16) & 0xF];
|
||||
str[5] = hex_lookup[(val >> 20) & 0xF];
|
||||
str[8] = hex_lookup[(val >> 24) & 0xF];
|
||||
str[7] = hex_lookup[(val >> 28) & 0xF];
|
||||
//
|
||||
syslog(str);
|
||||
//signal_led(false);
|
||||
res.cmd = (messages::id) 'B';
|
||||
res.ret = OK;
|
||||
res.val = 1;
|
||||
} else if(data[0] == 'T') {
|
||||
// Disable LED
|
||||
uint32_t val = data[4] | (data[5] << 8) | (data[6] << 16) | (data[7] << 24);
|
||||
top_color.r = data[7];
|
||||
top_color.g = data[6];
|
||||
top_color.b = data[5];
|
||||
str[0] = 'T';
|
||||
str[2] = hex_lookup[val & 0xF];
|
||||
str[1] = hex_lookup[(val >> 4) & 0xF];
|
||||
str[4] = hex_lookup[(val >> 8) & 0xF];
|
||||
str[3] = hex_lookup[(val >> 12) & 0xF];
|
||||
str[6] = hex_lookup[(val >> 16) & 0xF];
|
||||
str[5] = hex_lookup[(val >> 20) & 0xF];
|
||||
str[8] = hex_lookup[(val >> 24) & 0xF];
|
||||
str[7] = hex_lookup[(val >> 28) & 0xF];
|
||||
syslog(str);
|
||||
//signal_led(false);
|
||||
res.cmd = (messages::id) 'T';
|
||||
res.ret = OK;
|
||||
res.val = 1;
|
||||
} else if(data[0] == 'D') {
|
||||
// Disable LED
|
||||
syslog("G\n");
|
||||
|
|
|
@ -259,9 +259,17 @@
|
|||
</header>
|
||||
<footer>
|
||||
<label>
|
||||
<input type="checkbox" name="onoffswitch" id="led-switch" onclick="gpio()">
|
||||
<input type="checkbox" name="onoffswitch" id="led-switch" onclick="gpio(this.value)">
|
||||
<span class="toggle button">toggle signal led</span>
|
||||
</label>
|
||||
<label>
|
||||
<span>toggle signal led</span>
|
||||
<input type="color" onchange="colorTop(this.value)">
|
||||
</label>
|
||||
<label>
|
||||
<span>toggle signal led</span>
|
||||
<input type="color" onchange="colorBottom(this.value)">
|
||||
</label>
|
||||
</footer>
|
||||
</article>
|
||||
</div>
|
||||
|
@ -413,13 +421,31 @@
|
|||
ws.send(data);
|
||||
}
|
||||
|
||||
function gpio() {
|
||||
if (document.getElementById('led-switch').checked)
|
||||
function gpio(val) {
|
||||
if (val)
|
||||
wsWrite('E');
|
||||
else
|
||||
wsWrite('D');
|
||||
}
|
||||
|
||||
function colorTop(val) {
|
||||
var header = new ArrayBuffer(8);
|
||||
var headerview = new DataView(header);
|
||||
headerview.setChar(0, 'T');
|
||||
headerview.setInt32(4, parseInt(val.substring(1), 16));
|
||||
console.log(buf2hex(header));
|
||||
wsWrite(header);
|
||||
}
|
||||
|
||||
function colorBottom(val) {
|
||||
var header = new ArrayBuffer(8);
|
||||
var headerview = new DataView(header);
|
||||
headerview.setChar(0, 'B');
|
||||
headerview.setInt32(4, parseInt(val.substring(1), 16));
|
||||
console.log(buf2hex(header));
|
||||
wsWrite(header);
|
||||
}
|
||||
|
||||
window.onload = function () {
|
||||
wsOpen();
|
||||
startPolling();
|
||||
|
|
Loading…
Reference in a new issue