From cf0ed5c4bd07e191088977722010e9eec94a7c05 Mon Sep 17 00:00:00 2001 From: Selene ToyKeeper Date: Fri, 3 Nov 2023 09:07:37 -0600 Subject: moved variant builds under their parent, like "d4-219" -> "d4/219" --- hw/hank/emisar-2ch-fet/anduril.h | 113 ----------------- hw/hank/emisar-2ch-fet/hwdef.c | 206 ------------------------------ hw/hank/emisar-2ch-fet/hwdef.h | 209 ------------------------------- hw/hank/emisar-2ch/fet/anduril.h | 113 +++++++++++++++++ hw/hank/emisar-2ch/fet/hwdef.c | 206 ++++++++++++++++++++++++++++++ hw/hank/emisar-2ch/fet/hwdef.h | 209 +++++++++++++++++++++++++++++++ hw/hank/emisar-d18-219/anduril.h | 18 --- hw/hank/emisar-d18/219/anduril.h | 18 +++ hw/hank/emisar-d1v2-7135-fet/anduril.h | 32 ----- hw/hank/emisar-d1v2-linear-fet/anduril.h | 30 ----- hw/hank/emisar-d1v2-nofet/anduril.h | 24 ---- hw/hank/emisar-d1v2/7135-fet/anduril.h | 32 +++++ hw/hank/emisar-d1v2/linear-fet/anduril.h | 30 +++++ hw/hank/emisar-d1v2/nofet/anduril.h | 24 ++++ hw/hank/emisar-d4-219/anduril.h | 17 --- hw/hank/emisar-d4/219/anduril.h | 17 +++ hw/hank/emisar-d4s-219/anduril.h | 17 --- hw/hank/emisar-d4s/219/anduril.h | 17 +++ hw/hank/emisar-d4sv2-219/anduril.h | 18 --- hw/hank/emisar-d4sv2/219/anduril.h | 18 +++ hw/hank/emisar-d4v2-219/anduril.h | 17 --- hw/hank/emisar-d4v2-nofet/anduril.h | 62 --------- hw/hank/emisar-d4v2-nofet/hwdef.c | 55 -------- hw/hank/emisar-d4v2/219/anduril.h | 17 +++ hw/hank/emisar-d4v2/nofet/anduril.h | 62 +++++++++ hw/hank/emisar-d4v2/nofet/hwdef.c | 55 ++++++++ hw/hank/noctigon-dm11-boost/anduril.h | 91 -------------- hw/hank/noctigon-dm11-boost/hwdef.c | 97 -------------- hw/hank/noctigon-dm11-boost/hwdef.h | 206 ------------------------------ hw/hank/noctigon-dm11-nofet/anduril.h | 49 -------- hw/hank/noctigon-dm11-sbt90/anduril.h | 46 ------- hw/hank/noctigon-dm11/boost/anduril.h | 91 ++++++++++++++ hw/hank/noctigon-dm11/boost/hwdef.c | 97 ++++++++++++++ hw/hank/noctigon-dm11/boost/hwdef.h | 206 ++++++++++++++++++++++++++++++ hw/hank/noctigon-dm11/nofet/anduril.h | 49 ++++++++ hw/hank/noctigon-dm11/sbt90/anduril.h | 46 +++++++ hw/hank/noctigon-k1-boost/anduril.h | 96 -------------- hw/hank/noctigon-k1-boost/hwdef.h | 188 --------------------------- hw/hank/noctigon-k1-sbt90/anduril.h | 96 -------------- hw/hank/noctigon-k1-sbt90/hwdef.h | 177 -------------------------- hw/hank/noctigon-k1/boost/anduril.h | 96 ++++++++++++++ hw/hank/noctigon-k1/boost/hwdef.h | 188 +++++++++++++++++++++++++++ hw/hank/noctigon-k1/sbt90/anduril.h | 96 ++++++++++++++ hw/hank/noctigon-k1/sbt90/hwdef.h | 177 ++++++++++++++++++++++++++ hw/hank/noctigon-k9.3-219/anduril.h | 15 --- hw/hank/noctigon-k9.3-nofet/anduril.h | 12 -- hw/hank/noctigon-k9.3/219/anduril.h | 15 +++ hw/hank/noctigon-k9.3/anduril.h | 2 +- hw/hank/noctigon-k9.3/nofet/anduril.h | 12 ++ hw/hank/noctigon-kr4-219/anduril.h | 17 --- hw/hank/noctigon-kr4-219b/anduril.h | 17 --- hw/hank/noctigon-kr4-2ch/anduril.h | 16 --- hw/hank/noctigon-kr4-2ch/hwdef.h | 47 ------- hw/hank/noctigon-kr4-boost/anduril.h | 16 --- hw/hank/noctigon-kr4-boost/hwdef.h | 57 --------- hw/hank/noctigon-kr4-nofet/anduril.h | 66 ---------- hw/hank/noctigon-kr4-nofet/hwdef.c | 60 --------- hw/hank/noctigon-kr4/219/anduril.h | 17 +++ hw/hank/noctigon-kr4/219b/anduril.h | 17 +++ hw/hank/noctigon-kr4/2ch/anduril.h | 16 +++ hw/hank/noctigon-kr4/2ch/hwdef.h | 47 +++++++ hw/hank/noctigon-kr4/boost/anduril.h | 16 +++ hw/hank/noctigon-kr4/boost/hwdef.h | 57 +++++++++ hw/hank/noctigon-kr4/nofet/anduril.h | 66 ++++++++++ hw/hank/noctigon-kr4/nofet/hwdef.c | 60 +++++++++ 65 files changed, 2188 insertions(+), 2188 deletions(-) delete mode 100644 hw/hank/emisar-2ch-fet/anduril.h delete mode 100644 hw/hank/emisar-2ch-fet/hwdef.c delete mode 100644 hw/hank/emisar-2ch-fet/hwdef.h create mode 100644 hw/hank/emisar-2ch/fet/anduril.h create mode 100644 hw/hank/emisar-2ch/fet/hwdef.c create mode 100644 hw/hank/emisar-2ch/fet/hwdef.h delete mode 100644 hw/hank/emisar-d18-219/anduril.h create mode 100644 hw/hank/emisar-d18/219/anduril.h delete mode 100644 hw/hank/emisar-d1v2-7135-fet/anduril.h delete mode 100644 hw/hank/emisar-d1v2-linear-fet/anduril.h delete mode 100644 hw/hank/emisar-d1v2-nofet/anduril.h create mode 100644 hw/hank/emisar-d1v2/7135-fet/anduril.h create mode 100644 hw/hank/emisar-d1v2/linear-fet/anduril.h create mode 100644 hw/hank/emisar-d1v2/nofet/anduril.h delete mode 100644 hw/hank/emisar-d4-219/anduril.h create mode 100644 hw/hank/emisar-d4/219/anduril.h delete mode 100644 hw/hank/emisar-d4s-219/anduril.h create mode 100644 hw/hank/emisar-d4s/219/anduril.h delete mode 100644 hw/hank/emisar-d4sv2-219/anduril.h create mode 100644 hw/hank/emisar-d4sv2/219/anduril.h delete mode 100644 hw/hank/emisar-d4v2-219/anduril.h delete mode 100644 hw/hank/emisar-d4v2-nofet/anduril.h delete mode 100644 hw/hank/emisar-d4v2-nofet/hwdef.c create mode 100644 hw/hank/emisar-d4v2/219/anduril.h create mode 100644 hw/hank/emisar-d4v2/nofet/anduril.h create mode 100644 hw/hank/emisar-d4v2/nofet/hwdef.c delete mode 100644 hw/hank/noctigon-dm11-boost/anduril.h delete mode 100644 hw/hank/noctigon-dm11-boost/hwdef.c delete mode 100644 hw/hank/noctigon-dm11-boost/hwdef.h delete mode 100644 hw/hank/noctigon-dm11-nofet/anduril.h delete mode 100644 hw/hank/noctigon-dm11-sbt90/anduril.h create mode 100644 hw/hank/noctigon-dm11/boost/anduril.h create mode 100644 hw/hank/noctigon-dm11/boost/hwdef.c create mode 100644 hw/hank/noctigon-dm11/boost/hwdef.h create mode 100644 hw/hank/noctigon-dm11/nofet/anduril.h create mode 100644 hw/hank/noctigon-dm11/sbt90/anduril.h delete mode 100644 hw/hank/noctigon-k1-boost/anduril.h delete mode 100644 hw/hank/noctigon-k1-boost/hwdef.h delete mode 100644 hw/hank/noctigon-k1-sbt90/anduril.h delete mode 100644 hw/hank/noctigon-k1-sbt90/hwdef.h create mode 100644 hw/hank/noctigon-k1/boost/anduril.h create mode 100644 hw/hank/noctigon-k1/boost/hwdef.h create mode 100644 hw/hank/noctigon-k1/sbt90/anduril.h create mode 100644 hw/hank/noctigon-k1/sbt90/hwdef.h delete mode 100644 hw/hank/noctigon-k9.3-219/anduril.h delete mode 100644 hw/hank/noctigon-k9.3-nofet/anduril.h create mode 100644 hw/hank/noctigon-k9.3/219/anduril.h create mode 100644 hw/hank/noctigon-k9.3/nofet/anduril.h delete mode 100644 hw/hank/noctigon-kr4-219/anduril.h delete mode 100644 hw/hank/noctigon-kr4-219b/anduril.h delete mode 100644 hw/hank/noctigon-kr4-2ch/anduril.h delete mode 100644 hw/hank/noctigon-kr4-2ch/hwdef.h delete mode 100644 hw/hank/noctigon-kr4-boost/anduril.h delete mode 100644 hw/hank/noctigon-kr4-boost/hwdef.h delete mode 100644 hw/hank/noctigon-kr4-nofet/anduril.h delete mode 100644 hw/hank/noctigon-kr4-nofet/hwdef.c create mode 100644 hw/hank/noctigon-kr4/219/anduril.h create mode 100644 hw/hank/noctigon-kr4/219b/anduril.h create mode 100644 hw/hank/noctigon-kr4/2ch/anduril.h create mode 100644 hw/hank/noctigon-kr4/2ch/hwdef.h create mode 100644 hw/hank/noctigon-kr4/boost/anduril.h create mode 100644 hw/hank/noctigon-kr4/boost/hwdef.h create mode 100644 hw/hank/noctigon-kr4/nofet/anduril.h create mode 100644 hw/hank/noctigon-kr4/nofet/hwdef.c (limited to 'hw/hank') diff --git a/hw/hank/emisar-2ch-fet/anduril.h b/hw/hank/emisar-2ch-fet/anduril.h deleted file mode 100644 index 03ad748..0000000 --- a/hw/hank/emisar-2ch-fet/anduril.h +++ /dev/null @@ -1,113 +0,0 @@ -// Emisar 2-channel generic (plus FET) config options for Anduril (based on Noctigon K9.3) -// Copyright (C) 2021-2023 Selene ToyKeeper -// SPDX-License-Identifier: GPL-3.0-or-later -#pragma once - -#define MODEL_NUMBER "0136" -#include "hank/emisar-2ch-fet/hwdef.h" -#include "hank/anduril.h" -// ATTINY: 1634 - -// this light has three aux LED channels: R, G, B -#define USE_AUX_RGB_LEDS -// the aux LEDs are front-facing, so turn them off while main LEDs are on -// it also has an independent LED in the button -#define USE_BUTTON_LED -// TODO: the whole "indicator LED" thing needs to be refactored into -// "aux LED(s)" and "button LED(s)" since they work a bit differently -// enabling this option breaks the button LED on D4v2.5 -#ifdef USE_INDICATOR_LED_WHILE_RAMPING -#undef USE_INDICATOR_LED_WHILE_RAMPING -#endif - -// channel modes... -// CM_CH1, CM_CH2, CM_BOTH, CM_BLEND, CM_AUTO -// enable max brightness out of the box -#define DEFAULT_CHANNEL_MODE CM_BOTH - -#define USE_CONFIG_COLORS - -// blink numbers on the main LEDs by default (but allow user to change it) -#define DEFAULT_BLINK_CHANNEL CM_BOTH - -#define POLICE_COLOR_STROBE_CH1 CM_CH1 -#define POLICE_COLOR_STROBE_CH2 CM_CH2 - -// how much to increase total brightness at middle tint -// (0 = 100% brightness, 64 = 200% brightness) -#define TINT_RAMPING_CORRECTION 0 // none, linear regulator doesn't need it - - -// channel 1 / main LEDs (w/ DD FET) -// output: unknown, 1750 lm? -// FET: unknown, 3000 lm? -// channel 2 -// output: unknown, 1750 lm? -// combined: 4000 to 5000 lm? -#define RAMP_SIZE 150 - -// linear+FET ramp: maxreg at 140/150 -// level_calc.py 5.01 2 150 7135 1 0.1 1924 FET 1 10 2600 --pwm dyn:68:4096:255:3 --clock 8:16:0 -// linear segment -#define PWM1_LEVELS 1,1,1,1,1,1,1,1,1,1,1,1,1,2,2,2,2,2,2,2,2,3,3,3,3,3,3,3,4,4,4,4,4,4,4,4,5,5,5,5,5,5,5,5,5,6,6,6,6,6,6,7,7,7,7,8,8,8,9,9,9,10,10,11,12,13,13,14,15,16,17,17,18,19,20,21,22,23,25,26,27,28,30,31,33,34,36,37,39,41,43,44,46,48,50,53,55,57,60,62,65,67,70,73,76,79,82,85,88,92,95,99,103,106,110,114,119,123,127,132,137,142,147,152,157,162,168,174,179,185,192,198,204,211,218,225,232,240,247,255,255,255,255,255,255,255,255,255,255,255 -// DD FET segment -#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,20,44,68,93,118,144,171,198,226,255 -// PWM TOPS values -#define PWM3_LEVELS 4096,3831,3570,3314,3063,2817,2577,2342,2115,1894,1682,1477,1281,2237,2005,1784,1576,1380,1196,1111,1026,1442,1348,1215,1091,976,871,774,1031,942,860,784,714,650,591,538,652,602,555,513,473,437,403,372,343,398,370,345,322,299,278,311,292,273,255,278,261,245,263,247,232,246,231,243,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 - -// linear-only ramp -// level_calc.py 3.11 1 150 7135 1 0.1 1750 --pwm dyn:64:4096:255:3 --clock 8:16:0 -#define PWM4_LEVELS 1,1,1,1,1,1,2,2,2,3,3,3,4,4,4,5,5,6,6,6,7,7,7,8,8,8,9,9,9,10,10,10,10,10,10,11,11,11,11,11,11,11,12,12,12,12,12,12,13,13,13,14,14,14,15,15,16,17,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,33,34,35,37,38,39,41,42,44,45,47,48,50,52,53,55,57,59,61,63,65,67,69,71,73,75,77,79,82,84,86,89,91,94,97,99,102,105,107,110,113,116,119,122,125,128,132,135,138,141,145,148,152,156,159,163,167,170,174,178,182,186,190,195,199,203,208,212,217,221,226,230,235,240,245,250,255 -// PWM_TOPS values for linear-only ramp -#define PWM5_LEVELS 4096,3681,3247,2794,2328,1856,2937,2393,1860,2690,2273,1875,2281,1959,1658,1893,1646,1774,1569,1381,1466,1309,1166,1224,1104,996,1033,942,858,882,810,746,687,634,586,604,561,522,487,454,425,397,409,385,362,341,321,302,311,295,279,286,271,257,263,250,255,258,246,249,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 - -#define DEFAULT_LEVEL 75 -#define MAX_1x7135 140 -#define MAX_Nx7135 MAX_1x7135 -#define HALFSPEED_LEVEL 16 -#define QUARTERSPEED_LEVEL 8 - -#define RAMP_SMOOTH_FLOOR 10 // level 1 is unreliable (?) -#define RAMP_SMOOTH_CEIL 140 -// 10, 31, 53, [75], 96, 118, [140] -#define RAMP_DISCRETE_FLOOR 10 -#define RAMP_DISCRETE_CEIL RAMP_SMOOTH_CEIL -#define RAMP_DISCRETE_STEPS 7 - -// safe limit highest regulated power (no FET or turbo) -// 10, 42, [75], 107, 140 -#define SIMPLE_UI_FLOOR RAMP_DISCRETE_FLOOR -#define SIMPLE_UI_CEIL RAMP_DISCRETE_CEIL -#define SIMPLE_UI_STEPS 5 - -// stop panicking at ~1500 lm -#define THERM_FASTER_LEVEL 130 -#define MIN_THERM_STEPDOWN 65 // should be above highest dyn_pwm level - -#define USE_POLICE_COLOR_STROBE_MODE -#undef TACTICAL_LEVELS -#define TACTICAL_LEVELS 140,30,(RAMP_SIZE+3) // high, low, police strobe - -// use the brightest setting for strobe -#define STROBE_BRIGHTNESS MAX_LEVEL -// slow down party strobe; this driver can't pulse for 1ms or less -#define PARTY_STROBE_ONTIME 2 -// TODO: change speed per channel mode -// (the FET is really fast, but the regulator is not) -//#undef PARTY_STROBE_ONTIME - -// the default of 26 looks a bit flat, so increase it -#define CANDLE_AMPLITUDE 33 - -// the power regulator is a bit slow, so push it harder for a quick response from off -#define DEFAULT_JUMP_START_LEVEL 40 -#define BLINK_BRIGHTNESS 45 -#define BLINK_ONCE_TIME 12 // longer blink, since main LEDs are slow - -#define THERM_CAL_OFFSET 5 - -// don't blink while ramping -#ifdef BLINK_AT_RAMP_MIDDLE -#undef BLINK_AT_RAMP_MIDDLE -#endif - diff --git a/hw/hank/emisar-2ch-fet/hwdef.c b/hw/hank/emisar-2ch-fet/hwdef.c deleted file mode 100644 index 4309a42..0000000 --- a/hw/hank/emisar-2ch-fet/hwdef.c +++ /dev/null @@ -1,206 +0,0 @@ -// Emisar generic 2-channel + DD FET w/ tint ramping -// Copyright (C) 2021-2023 Selene ToyKeeper -// SPDX-License-Identifier: GPL-3.0-or-later - -#pragma once - -#include "fsm/chan-rgbaux.c" - - -void set_level_zero(); - -void set_level_ch1(uint8_t level); -void set_level_ch2(uint8_t level); -void set_level_both(uint8_t level); -void set_level_blend(uint8_t level); -void set_level_auto(uint8_t level); - -bool gradual_tick_ch1(uint8_t gt); -bool gradual_tick_ch2(uint8_t gt); -bool gradual_tick_both(uint8_t gt); -bool gradual_tick_blend(uint8_t gt); -bool gradual_tick_auto(uint8_t gt); - - -Channel channels[] = { - { // channel 1 only - .set_level = set_level_ch1, - .gradual_tick = gradual_tick_ch1, - .has_args = 0 - }, - { // channel 2 only - .set_level = set_level_ch2, - .gradual_tick = gradual_tick_ch2, - .has_args = 0 - }, - { // both channels, tied together (max "200%" power) - .set_level = set_level_both, - .gradual_tick = gradual_tick_both, - .has_args = 0 - }, - { // both channels, manual blend (max "100%" power) - .set_level = set_level_blend, - .gradual_tick = gradual_tick_blend, - .has_args = 1 - }, - { // both channels, auto blend - .set_level = set_level_auto, - .gradual_tick = gradual_tick_auto, - .has_args = 1 - }, - RGB_AUX_CHANNELS -}; - - -// set new values for both channels, -// handling any possible combination -// and any before/after state -void set_pwms(uint8_t ch1_pwm, uint8_t ch2_pwm, uint8_t ch3_pwm, uint16_t top) { - bool was_on = (CH1_PWM>0) | (CH2_PWM>0) | (CH3_PWM>0); - bool now_on = (ch1_pwm>0) | (ch2_pwm>0) | (ch3_pwm>0); - - if (! now_on) { - CH1_PWM = 0; // linear - CH2_PWM = 0; // linear - CH3_PWM = 0; // DD FET - PWM_TOP = PWM_TOP_INIT; - PWM_CNT = 0; - CH1_ENABLE_PORT &= ~(1 << CH1_ENABLE_PIN); // disable opamp - CH2_ENABLE_PORT &= ~(1 << CH2_ENABLE_PIN); // disable opamp - return; - } - - if (ch1_pwm) - CH1_ENABLE_PORT |= (1 << CH1_ENABLE_PIN); // enable opamp - else - CH1_ENABLE_PORT &= ~(1 << CH1_ENABLE_PIN); // disable opamp - - if (ch2_pwm) - CH2_ENABLE_PORT |= (1 << CH2_ENABLE_PIN); // enable opamp - else - CH2_ENABLE_PORT &= ~(1 << CH2_ENABLE_PIN); // disable opamp - - CH1_PWM = ch1_pwm; - CH2_PWM = ch2_pwm; - CH3_PWM = ch3_pwm; - - // manual phase sync when changing level while already on - if (was_on && now_on) while(PWM_CNT > (top - 32)) {} - - PWM_TOP = top; - - // reset phase when turning on or off - //if ((! was_on) | (! now_on)) PWM_CNT = 0; - if (! was_on) PWM_CNT = 0; -} - -void set_level_zero() { - return set_pwms(0, 0, 0, PWM_TOP_INIT); -} - -void set_level_ch1(uint8_t level) { - uint8_t pwm1 = PWM_GET8 (pwm1_levels, level); - uint8_t pwm3 = PWM_GET8 (pwm2_levels, level); - uint16_t top = PWM_GET16(pwm3_levels, level); - set_pwms(pwm1, 0, pwm3, top); -} - -void set_level_ch2(uint8_t level) { - uint8_t pwm2 = PWM_GET8 (pwm4_levels, level); - uint16_t top = PWM_GET16(pwm5_levels, level); - set_pwms(0, pwm2, 0, top); -} - -void set_level_both(uint8_t level) { - uint8_t pwm1 = PWM_GET8 (pwm1_levels, level); - uint8_t pwm3 = PWM_GET8 (pwm2_levels, level); - uint16_t top = PWM_GET16(pwm3_levels, level); - set_pwms(pwm1, pwm1, pwm3, top); -} - -void set_level_blend(uint8_t level) { - uint16_t pwm1, pwm2; - uint8_t pwm3 = PWM_GET8 (pwm2_levels, level); // DD FET - //uint16_t brightness = PWM_GET8 (pwm1_levels, level) << 1; - uint16_t brightness = PWM_GET8 (pwm1_levels, level) + pwm3; - uint16_t top = PWM_GET16(pwm3_levels, level); - uint8_t blend = cfg.channel_mode_args[channel_mode]; - - calc_2ch_blend(&pwm1, &pwm2, brightness, top, blend); - - set_pwms(pwm1, pwm2, pwm3, top); -} - -void set_level_auto(uint8_t level) { - uint16_t pwm1, pwm2; - uint8_t brightness = PWM_GET8 (pwm4_levels, level); - uint16_t top = PWM_GET16(pwm5_levels, level); - uint8_t blend = 255 * (uint16_t)level / RAMP_SIZE; - if (cfg.channel_mode_args[channel_mode] & 0b01000000) - blend = 255 - blend; - - calc_2ch_blend(&pwm1, &pwm2, brightness, top, blend); - - set_pwms(pwm1, pwm2, 0, top); -} - - -///// bump each channel toward a target value ///// -bool gradual_adjust(uint8_t ch1_pwm, uint8_t ch2_pwm, uint8_t ch3_pwm) { - GRADUAL_ADJUST_STACKED(ch1_pwm, CH1_PWM, PWM_TOP_INIT); - GRADUAL_ADJUST_STACKED(ch2_pwm, CH2_PWM, PWM_TOP_INIT); - GRADUAL_ADJUST_SIMPLE (ch3_pwm, CH3_PWM); - - // check for completion - if ((ch1_pwm == CH1_PWM) - && (ch2_pwm == CH2_PWM) - && (ch3_pwm == CH3_PWM)) { - return true; // done - } - return false; // not done yet -} - -bool gradual_tick_ch1(uint8_t gt) { - uint8_t pwm1 = PWM_GET8(pwm1_levels, gt); - uint8_t pwm3 = PWM_GET8(pwm2_levels, gt); - return gradual_adjust(pwm1, 0, pwm3); -} - -bool gradual_tick_ch2(uint8_t gt) { - uint8_t pwm2 = PWM_GET8(pwm4_levels, gt); - return gradual_adjust(0, pwm2, 0); -} - -bool gradual_tick_both(uint8_t gt) { - uint8_t pwm1 = PWM_GET8(pwm1_levels, gt); - uint8_t pwm3 = PWM_GET8(pwm2_levels, gt); - return gradual_adjust(pwm1, pwm1, pwm3); -} - -bool gradual_tick_blend(uint8_t level) { - uint16_t pwm1, pwm2; - uint8_t pwm3 = PWM_GET8 (pwm2_levels, level); // DD FET - //uint16_t brightness = PWM_GET8 (pwm1_levels, level) << 1; - uint16_t brightness = PWM_GET8 (pwm1_levels, level) + pwm3; - uint16_t top = PWM_GET16(pwm3_levels, level); - uint8_t blend = cfg.channel_mode_args[channel_mode]; - - calc_2ch_blend(&pwm1, &pwm2, brightness, top, blend); - - return gradual_adjust(pwm1, pwm2, pwm3); -} - -bool gradual_tick_auto(uint8_t level) { - uint16_t pwm1, pwm2; - uint8_t brightness = PWM_GET8 (pwm4_levels, level); - uint16_t top = PWM_GET16(pwm5_levels, level); - uint8_t blend = 255 * (uint16_t)level / RAMP_SIZE; - if (cfg.channel_mode_args[channel_mode] & 0b01000000) - blend = 255 - blend; - - calc_2ch_blend(&pwm1, &pwm2, brightness, top, blend); - - return gradual_adjust(pwm1, pwm2, 0); -} - - diff --git a/hw/hank/emisar-2ch-fet/hwdef.h b/hw/hank/emisar-2ch-fet/hwdef.h deleted file mode 100644 index a429a6c..0000000 --- a/hw/hank/emisar-2ch-fet/hwdef.h +++ /dev/null @@ -1,209 +0,0 @@ -// Emisar 2-channel generic w/ tint ramping + DD FET -// Copyright (C) 2021-2023 Selene ToyKeeper -// SPDX-License-Identifier: GPL-3.0-or-later -#pragma once - -/* - * Pin / Name / Function - * 1 PA6 ch2 LED PWM (linear) (PWM1B) - * 2 PA5 R: red aux LED (PWM0B) - * 3 PA4 G: green aux LED - * 4 PA3 B: blue aux LED - * 5 PA2 button LED - * 6 PA1 Opamp 2 enable (channel 2 LEDs) - * 7 PA0 Opamp 1 enable (channel 1 LEDs) - * 8 GND GND - * 9 VCC VCC - * 10 PC5 (none) - * 11 PC4 (none) - * 12 PC3 RESET - * 13 PC2 (none) - * 14 PC1 SCK - * 15 PC0 ch1 LED PWM (FET) (PWM0A, 8-bit) - * 16 PB3 ch1 LED PWM (linear) (PWM1A) - * 17 PB2 MISO - * 18 PB1 MOSI / battery voltage (ADC6) - * 19 PB0 (none) - * 20 PA7 e-switch (PCINT7) - * ADC12 thermal sensor - * - * Both sets of LEDs use one pin to turn the Opamp on/off, - * and one pin to control the Opamp power level. - * The first channel also has a direct-drive FET for turbo. - */ - -#define ATTINY 1634 -#include - -#define HWDEF_C_FILE hank/emisar-2ch-fet/hwdef.c - -// allow using aux LEDs as extra channel modes -#include "fsm/chan-rgbaux.h" - -// channel modes: -// * 0. channel 1 only (linear + DD FET) -// * 1. channel 2 only (linear) -// * 2. both channels, tied together, max "200%" power + DD FET at top of ramp -// * 3. both channels, manual blend, max "100%" power + "200%" and DD FET at top of ramp -// * 4. both channels, auto blend, reversible (linear only) -#define NUM_CHANNEL_MODES (5 + NUM_RGB_AUX_CHANNEL_MODES) -enum channel_modes_e { - CM_CH1 = 0, - CM_CH2, - CM_BOTH, - CM_BLEND, - CM_AUTO, - RGB_AUX_ENUMS -}; - -// right-most bit first, modes are in fedcba9876543210 order -#define CHANNEL_MODES_ENABLED 0b0000000000011111 -#define USE_CHANNEL_MODE_ARGS -// _, _, _, 128=middle CCT, 0=warm-to-cool -#define CHANNEL_MODE_ARGS 0,0,0,128,0,RGB_AUX_CM_ARGS - -// can use some of the common handlers -#define USE_CALC_2CH_BLEND - - -#define PWM_CHANNELS 3 // old, remove this - -#define PWM_BITS 16 // 0 to 16383 at variable Hz, not 0 to 255 at 16 kHz -#define PWM_GET PWM_GET8 -#define PWM_DATATYPE uint16_t -#define PWM_DATATYPE2 uint16_t // only needs 32-bit if ramp values go over 255 -#define PWM1_DATATYPE uint8_t // linear part of linear+FET ramp -#define PWM2_DATATYPE uint8_t // DD FET part of linear+FET ramp -#define PWM3_DATATYPE uint16_t // linear+FET ramp tops -#define PWM4_DATATYPE uint8_t // linear-only ramp -#define PWM5_DATATYPE uint16_t // linear-only ramp tops - -// PWM parameters of both channels are tied together because they share a counter -#define PWM_TOP ICR1 // holds the TOP value for for variable-resolution PWM -#define PWM_TOP_INIT 255 // highest value used in top half of ramp -#define PWM_CNT TCNT1 // for dynamic PWM, reset phase - -// main LEDs, linear -#define CH1_PIN PB3 // pin 16, Opamp reference -#define CH1_PWM OCR1A // OCR1A is the output compare register for PB3 -#define CH1_ENABLE_PIN PA0 // pin 7, Opamp power -#define CH1_ENABLE_PORT PORTA // control port for PA0 - -// 2nd LEDs, linear -#define CH2_PIN PA6 // pin 1, 2nd LED Opamp reference -#define CH2_PWM OCR1B // OCR1B is the output compare register for PA6 -#define CH2_ENABLE_PIN PA1 // pin 6, Opamp power -#define CH2_ENABLE_PORT PORTA // control port for PA1 - -// main LEDs, DD FET -#define CH3_PIN PC0 // pin 15, DD FET PWM -#define CH3_PWM OCR0A // OCR0A is the output compare register for PC0 - -// e-switch -#ifndef SWITCH_PIN -#define SWITCH_PIN PA7 // pin 20 -#define SWITCH_PCINT PCINT7 // pin 20 pin change interrupt -#define SWITCH_PCIE PCIE0 // PCIE1 is for PCINT[7:0] -#define SWITCH_PCMSK PCMSK0 // PCMSK1 is for PCINT[7:0] -#define SWITCH_PORT PINA // PINA or PINB or PINC -#define SWITCH_PUE PUEA // pullup group A -#define PCINT_vect PCINT0_vect // ISR for PCINT[7:0] -#endif - -#define USE_VOLTAGE_DIVIDER // use a dedicated pin, not VCC, because VCC input is flattened -#define VOLTAGE_PIN PB1 // Pin 18 / PB1 / ADC6 -// pin to ADC mappings are in DS table 19-4 -#define VOLTAGE_ADC ADC6D // digital input disable pin for PB1 -// DIDR0/DIDR1 mappings are in DS section 19.13.5, 19.13.6 -#define VOLTAGE_ADC_DIDR DIDR1 // DIDR channel for ADC6D -// DS tables 19-3, 19-4 -// Bit 7 6 5 4 3 2 1 0 -// REFS1 REFS0 REFEN ADC0EN MUX3 MUX2 MUX1 MUX0 -// MUX[3:0] = 0, 1, 1, 0 for ADC6 / PB1 -// divided by ... -// REFS[1:0] = 1, 0 for internal 1.1V reference -// other bits reserved -#define ADMUX_VOLTAGE_DIVIDER 0b10000110 -#define ADC_PRSCL 0x07 // clk/128 - -// Raw ADC readings at 4.4V and 2.2V -// calibrate the voltage readout here -// estimated / calculated values are: -// (voltage - D1) * (R2/(R2+R1) * 1024 / 1.1) -// D1, R1, R2 = 0, 330, 100 -#ifndef ADC_44 -//#define ADC_44 981 // raw value at 4.40V -#define ADC_44 967 // manually tweaked so 4.16V will blink out 4.2 -#endif -#ifndef ADC_22 -//#define ADC_22 489 // raw value at 2.20V -#define ADC_22 482 // manually tweaked so 4.16V will blink out 4.2 -#endif - -// this light has aux LEDs under the optic -#define AUXLED_R_PIN PA5 // pin 2 -#define AUXLED_G_PIN PA4 // pin 3 -#define AUXLED_B_PIN PA3 // pin 4 -#define AUXLED_RGB_PORT PORTA // PORTA or PORTB or PORTC -#define AUXLED_RGB_DDR DDRA // DDRA or DDRB or DDRC -#define AUXLED_RGB_PUE PUEA // PUEA or PUEB or PUEC - -#define BUTTON_LED_PIN PA2 // pin 5 -#define BUTTON_LED_PORT PORTA // for all "PA" pins -#define BUTTON_LED_DDR DDRA // for all "PA" pins -#define BUTTON_LED_PUE PUEA // for all "PA" pins - - -inline void hwdef_setup() { - // enable output ports - DDRC = (1 << CH3_PIN); - DDRB = (1 << CH1_PIN); - DDRA = (1 << CH2_PIN) - | (1 << AUXLED_R_PIN) - | (1 << AUXLED_G_PIN) - | (1 << AUXLED_B_PIN) - | (1 << BUTTON_LED_PIN) - | (1 << CH1_ENABLE_PIN) - | (1 << CH2_ENABLE_PIN) - ; - - // configure PWM - // Setup PWM. F_pwm = F_clkio / 2 / N / TOP, where N = prescale factor, TOP = top of counter - // pre-scale for timer: N = 1 - // Linear opamp PWM for both main and 2nd LEDs (10-bit) - // WGM1[3:0]: 1,0,1,0: PWM, Phase Correct, adjustable (DS table 12-5) - // CS1[2:0]: 0,0,1: clk/1 (No prescaling) (DS table 12-6) - // COM1A[1:0]: 1,0: PWM OC1A in the normal direction (DS table 12-4) - // COM1B[1:0]: 1,0: PWM OC1B in the normal direction (DS table 12-4) - TCCR1A = (1<0) | (CH2_PWM>0) | (CH3_PWM>0); + bool now_on = (ch1_pwm>0) | (ch2_pwm>0) | (ch3_pwm>0); + + if (! now_on) { + CH1_PWM = 0; // linear + CH2_PWM = 0; // linear + CH3_PWM = 0; // DD FET + PWM_TOP = PWM_TOP_INIT; + PWM_CNT = 0; + CH1_ENABLE_PORT &= ~(1 << CH1_ENABLE_PIN); // disable opamp + CH2_ENABLE_PORT &= ~(1 << CH2_ENABLE_PIN); // disable opamp + return; + } + + if (ch1_pwm) + CH1_ENABLE_PORT |= (1 << CH1_ENABLE_PIN); // enable opamp + else + CH1_ENABLE_PORT &= ~(1 << CH1_ENABLE_PIN); // disable opamp + + if (ch2_pwm) + CH2_ENABLE_PORT |= (1 << CH2_ENABLE_PIN); // enable opamp + else + CH2_ENABLE_PORT &= ~(1 << CH2_ENABLE_PIN); // disable opamp + + CH1_PWM = ch1_pwm; + CH2_PWM = ch2_pwm; + CH3_PWM = ch3_pwm; + + // manual phase sync when changing level while already on + if (was_on && now_on) while(PWM_CNT > (top - 32)) {} + + PWM_TOP = top; + + // reset phase when turning on or off + //if ((! was_on) | (! now_on)) PWM_CNT = 0; + if (! was_on) PWM_CNT = 0; +} + +void set_level_zero() { + return set_pwms(0, 0, 0, PWM_TOP_INIT); +} + +void set_level_ch1(uint8_t level) { + uint8_t pwm1 = PWM_GET8 (pwm1_levels, level); + uint8_t pwm3 = PWM_GET8 (pwm2_levels, level); + uint16_t top = PWM_GET16(pwm3_levels, level); + set_pwms(pwm1, 0, pwm3, top); +} + +void set_level_ch2(uint8_t level) { + uint8_t pwm2 = PWM_GET8 (pwm4_levels, level); + uint16_t top = PWM_GET16(pwm5_levels, level); + set_pwms(0, pwm2, 0, top); +} + +void set_level_both(uint8_t level) { + uint8_t pwm1 = PWM_GET8 (pwm1_levels, level); + uint8_t pwm3 = PWM_GET8 (pwm2_levels, level); + uint16_t top = PWM_GET16(pwm3_levels, level); + set_pwms(pwm1, pwm1, pwm3, top); +} + +void set_level_blend(uint8_t level) { + uint16_t pwm1, pwm2; + uint8_t pwm3 = PWM_GET8 (pwm2_levels, level); // DD FET + //uint16_t brightness = PWM_GET8 (pwm1_levels, level) << 1; + uint16_t brightness = PWM_GET8 (pwm1_levels, level) + pwm3; + uint16_t top = PWM_GET16(pwm3_levels, level); + uint8_t blend = cfg.channel_mode_args[channel_mode]; + + calc_2ch_blend(&pwm1, &pwm2, brightness, top, blend); + + set_pwms(pwm1, pwm2, pwm3, top); +} + +void set_level_auto(uint8_t level) { + uint16_t pwm1, pwm2; + uint8_t brightness = PWM_GET8 (pwm4_levels, level); + uint16_t top = PWM_GET16(pwm5_levels, level); + uint8_t blend = 255 * (uint16_t)level / RAMP_SIZE; + if (cfg.channel_mode_args[channel_mode] & 0b01000000) + blend = 255 - blend; + + calc_2ch_blend(&pwm1, &pwm2, brightness, top, blend); + + set_pwms(pwm1, pwm2, 0, top); +} + + +///// bump each channel toward a target value ///// +bool gradual_adjust(uint8_t ch1_pwm, uint8_t ch2_pwm, uint8_t ch3_pwm) { + GRADUAL_ADJUST_STACKED(ch1_pwm, CH1_PWM, PWM_TOP_INIT); + GRADUAL_ADJUST_STACKED(ch2_pwm, CH2_PWM, PWM_TOP_INIT); + GRADUAL_ADJUST_SIMPLE (ch3_pwm, CH3_PWM); + + // check for completion + if ((ch1_pwm == CH1_PWM) + && (ch2_pwm == CH2_PWM) + && (ch3_pwm == CH3_PWM)) { + return true; // done + } + return false; // not done yet +} + +bool gradual_tick_ch1(uint8_t gt) { + uint8_t pwm1 = PWM_GET8(pwm1_levels, gt); + uint8_t pwm3 = PWM_GET8(pwm2_levels, gt); + return gradual_adjust(pwm1, 0, pwm3); +} + +bool gradual_tick_ch2(uint8_t gt) { + uint8_t pwm2 = PWM_GET8(pwm4_levels, gt); + return gradual_adjust(0, pwm2, 0); +} + +bool gradual_tick_both(uint8_t gt) { + uint8_t pwm1 = PWM_GET8(pwm1_levels, gt); + uint8_t pwm3 = PWM_GET8(pwm2_levels, gt); + return gradual_adjust(pwm1, pwm1, pwm3); +} + +bool gradual_tick_blend(uint8_t level) { + uint16_t pwm1, pwm2; + uint8_t pwm3 = PWM_GET8 (pwm2_levels, level); // DD FET + //uint16_t brightness = PWM_GET8 (pwm1_levels, level) << 1; + uint16_t brightness = PWM_GET8 (pwm1_levels, level) + pwm3; + uint16_t top = PWM_GET16(pwm3_levels, level); + uint8_t blend = cfg.channel_mode_args[channel_mode]; + + calc_2ch_blend(&pwm1, &pwm2, brightness, top, blend); + + return gradual_adjust(pwm1, pwm2, pwm3); +} + +bool gradual_tick_auto(uint8_t level) { + uint16_t pwm1, pwm2; + uint8_t brightness = PWM_GET8 (pwm4_levels, level); + uint16_t top = PWM_GET16(pwm5_levels, level); + uint8_t blend = 255 * (uint16_t)level / RAMP_SIZE; + if (cfg.channel_mode_args[channel_mode] & 0b01000000) + blend = 255 - blend; + + calc_2ch_blend(&pwm1, &pwm2, brightness, top, blend); + + return gradual_adjust(pwm1, pwm2, 0); +} + + diff --git a/hw/hank/emisar-2ch/fet/hwdef.h b/hw/hank/emisar-2ch/fet/hwdef.h new file mode 100644 index 0000000..1569d41 --- /dev/null +++ b/hw/hank/emisar-2ch/fet/hwdef.h @@ -0,0 +1,209 @@ +// Emisar 2-channel generic w/ tint ramping + DD FET +// Copyright (C) 2021-2023 Selene ToyKeeper +// SPDX-License-Identifier: GPL-3.0-or-later +#pragma once + +/* + * Pin / Name / Function + * 1 PA6 ch2 LED PWM (linear) (PWM1B) + * 2 PA5 R: red aux LED (PWM0B) + * 3 PA4 G: green aux LED + * 4 PA3 B: blue aux LED + * 5 PA2 button LED + * 6 PA1 Opamp 2 enable (channel 2 LEDs) + * 7 PA0 Opamp 1 enable (channel 1 LEDs) + * 8 GND GND + * 9 VCC VCC + * 10 PC5 (none) + * 11 PC4 (none) + * 12 PC3 RESET + * 13 PC2 (none) + * 14 PC1 SCK + * 15 PC0 ch1 LED PWM (FET) (PWM0A, 8-bit) + * 16 PB3 ch1 LED PWM (linear) (PWM1A) + * 17 PB2 MISO + * 18 PB1 MOSI / battery voltage (ADC6) + * 19 PB0 (none) + * 20 PA7 e-switch (PCINT7) + * ADC12 thermal sensor + * + * Both sets of LEDs use one pin to turn the Opamp on/off, + * and one pin to control the Opamp power level. + * The first channel also has a direct-drive FET for turbo. + */ + +#define ATTINY 1634 +#include + +#define HWDEF_C_FILE hank/emisar-2ch/fet/hwdef.c + +// allow using aux LEDs as extra channel modes +#include "fsm/chan-rgbaux.h" + +// channel modes: +// * 0. channel 1 only (linear + DD FET) +// * 1. channel 2 only (linear) +// * 2. both channels, tied together, max "200%" power + DD FET at top of ramp +// * 3. both channels, manual blend, max "100%" power + "200%" and DD FET at top of ramp +// * 4. both channels, auto blend, reversible (linear only) +#define NUM_CHANNEL_MODES (5 + NUM_RGB_AUX_CHANNEL_MODES) +enum channel_modes_e { + CM_CH1 = 0, + CM_CH2, + CM_BOTH, + CM_BLEND, + CM_AUTO, + RGB_AUX_ENUMS +}; + +// right-most bit first, modes are in fedcba9876543210 order +#define CHANNEL_MODES_ENABLED 0b0000000000011111 +#define USE_CHANNEL_MODE_ARGS +// _, _, _, 128=middle CCT, 0=warm-to-cool +#define CHANNEL_MODE_ARGS 0,0,0,128,0,RGB_AUX_CM_ARGS + +// can use some of the common handlers +#define USE_CALC_2CH_BLEND + + +#define PWM_CHANNELS 3 // old, remove this + +#define PWM_BITS 16 // 0 to 16383 at variable Hz, not 0 to 255 at 16 kHz +#define PWM_GET PWM_GET8 +#define PWM_DATATYPE uint16_t +#define PWM_DATATYPE2 uint16_t // only needs 32-bit if ramp values go over 255 +#define PWM1_DATATYPE uint8_t // linear part of linear+FET ramp +#define PWM2_DATATYPE uint8_t // DD FET part of linear+FET ramp +#define PWM3_DATATYPE uint16_t // linear+FET ramp tops +#define PWM4_DATATYPE uint8_t // linear-only ramp +#define PWM5_DATATYPE uint16_t // linear-only ramp tops + +// PWM parameters of both channels are tied together because they share a counter +#define PWM_TOP ICR1 // holds the TOP value for for variable-resolution PWM +#define PWM_TOP_INIT 255 // highest value used in top half of ramp +#define PWM_CNT TCNT1 // for dynamic PWM, reset phase + +// main LEDs, linear +#define CH1_PIN PB3 // pin 16, Opamp reference +#define CH1_PWM OCR1A // OCR1A is the output compare register for PB3 +#define CH1_ENABLE_PIN PA0 // pin 7, Opamp power +#define CH1_ENABLE_PORT PORTA // control port for PA0 + +// 2nd LEDs, linear +#define CH2_PIN PA6 // pin 1, 2nd LED Opamp reference +#define CH2_PWM OCR1B // OCR1B is the output compare register for PA6 +#define CH2_ENABLE_PIN PA1 // pin 6, Opamp power +#define CH2_ENABLE_PORT PORTA // control port for PA1 + +// main LEDs, DD FET +#define CH3_PIN PC0 // pin 15, DD FET PWM +#define CH3_PWM OCR0A // OCR0A is the output compare register for PC0 + +// e-switch +#ifndef SWITCH_PIN +#define SWITCH_PIN PA7 // pin 20 +#define SWITCH_PCINT PCINT7 // pin 20 pin change interrupt +#define SWITCH_PCIE PCIE0 // PCIE1 is for PCINT[7:0] +#define SWITCH_PCMSK PCMSK0 // PCMSK1 is for PCINT[7:0] +#define SWITCH_PORT PINA // PINA or PINB or PINC +#define SWITCH_PUE PUEA // pullup group A +#define PCINT_vect PCINT0_vect // ISR for PCINT[7:0] +#endif + +#define USE_VOLTAGE_DIVIDER // use a dedicated pin, not VCC, because VCC input is flattened +#define VOLTAGE_PIN PB1 // Pin 18 / PB1 / ADC6 +// pin to ADC mappings are in DS table 19-4 +#define VOLTAGE_ADC ADC6D // digital input disable pin for PB1 +// DIDR0/DIDR1 mappings are in DS section 19.13.5, 19.13.6 +#define VOLTAGE_ADC_DIDR DIDR1 // DIDR channel for ADC6D +// DS tables 19-3, 19-4 +// Bit 7 6 5 4 3 2 1 0 +// REFS1 REFS0 REFEN ADC0EN MUX3 MUX2 MUX1 MUX0 +// MUX[3:0] = 0, 1, 1, 0 for ADC6 / PB1 +// divided by ... +// REFS[1:0] = 1, 0 for internal 1.1V reference +// other bits reserved +#define ADMUX_VOLTAGE_DIVIDER 0b10000110 +#define ADC_PRSCL 0x07 // clk/128 + +// Raw ADC readings at 4.4V and 2.2V +// calibrate the voltage readout here +// estimated / calculated values are: +// (voltage - D1) * (R2/(R2+R1) * 1024 / 1.1) +// D1, R1, R2 = 0, 330, 100 +#ifndef ADC_44 +//#define ADC_44 981 // raw value at 4.40V +#define ADC_44 967 // manually tweaked so 4.16V will blink out 4.2 +#endif +#ifndef ADC_22 +//#define ADC_22 489 // raw value at 2.20V +#define ADC_22 482 // manually tweaked so 4.16V will blink out 4.2 +#endif + +// this light has aux LEDs under the optic +#define AUXLED_R_PIN PA5 // pin 2 +#define AUXLED_G_PIN PA4 // pin 3 +#define AUXLED_B_PIN PA3 // pin 4 +#define AUXLED_RGB_PORT PORTA // PORTA or PORTB or PORTC +#define AUXLED_RGB_DDR DDRA // DDRA or DDRB or DDRC +#define AUXLED_RGB_PUE PUEA // PUEA or PUEB or PUEC + +#define BUTTON_LED_PIN PA2 // pin 5 +#define BUTTON_LED_PORT PORTA // for all "PA" pins +#define BUTTON_LED_DDR DDRA // for all "PA" pins +#define BUTTON_LED_PUE PUEA // for all "PA" pins + + +inline void hwdef_setup() { + // enable output ports + DDRC = (1 << CH3_PIN); + DDRB = (1 << CH1_PIN); + DDRA = (1 << CH2_PIN) + | (1 << AUXLED_R_PIN) + | (1 << AUXLED_G_PIN) + | (1 << AUXLED_B_PIN) + | (1 << BUTTON_LED_PIN) + | (1 << CH1_ENABLE_PIN) + | (1 << CH2_ENABLE_PIN) + ; + + // configure PWM + // Setup PWM. F_pwm = F_clkio / 2 / N / TOP, where N = prescale factor, TOP = top of counter + // pre-scale for timer: N = 1 + // Linear opamp PWM for both main and 2nd LEDs (10-bit) + // WGM1[3:0]: 1,0,1,0: PWM, Phase Correct, adjustable (DS table 12-5) + // CS1[2:0]: 0,0,1: clk/1 (No prescaling) (DS table 12-6) + // COM1A[1:0]: 1,0: PWM OC1A in the normal direction (DS table 12-4) + // COM1B[1:0]: 1,0: PWM OC1B in the normal direction (DS table 12-4) + TCCR1A = (1< (top - 32))) {} - PWM_TOP = top; - // force reset phase when turning on from zero - // (because otherwise the initial response is inconsistent) - if (! actual_level) PWM_CNT = 0; -} - -bool gradual_tick_main(uint8_t gt) { - PWM_DATATYPE pwm1 = PWM_GET(pwm1_levels, gt); - - GRADUAL_ADJUST_SIMPLE (pwm1, CH1_PWM); - - if ( (pwm1 == CH1_PWM) - ) { - return true; // done - } - return false; // not done yet -} - diff --git a/hw/hank/emisar-d4v2/219/anduril.h b/hw/hank/emisar-d4v2/219/anduril.h new file mode 100644 index 0000000..1022a04 --- /dev/null +++ b/hw/hank/emisar-d4v2/219/anduril.h @@ -0,0 +1,17 @@ +// Emisar D4v2-219 config options for Anduril +// Copyright (C) 2019-2023 Selene ToyKeeper +// SPDX-License-Identifier: GPL-3.0-or-later +#pragma once + +#include "hank/emisar-d4v2/anduril.h" +#undef MODEL_NUMBER +#define MODEL_NUMBER "0114" +// ATTINY: 1634 + +// don't turn off the low channel at turbo level +#undef LOW_PWM_LEVELS +#define LOW_PWM_LEVELS 1,1,2,2,3,3,4,4,5,6,7,8,9,10,12,13,14,15,17,19,20,22,24,26,29,31,34,36,39,42,45,48,51,55,59,62,66,70,75,79,84,89,93,99,104,110,115,121,127,134,140,147,154,161,168,176,184,192,200,209,217,226,236,245,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 +// 65% DDFET power +#undef HIGH_PWM_LEVELS +#define HIGH_PWM_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,13,15,16,17,18,19,21,22,23,25,26,27,28,30,32,33,34,36,38,39,41,42,44,46,47,49,51,53,55,57,59,61,63,65,67,69,71,73,75,78,80,82,84,87,90,92,94,97,99,102,104,108,110,113,116,119,121,125,127,130,134,136,140,143,146,149,153,156,159,163,166 + diff --git a/hw/hank/emisar-d4v2/nofet/anduril.h b/hw/hank/emisar-d4v2/nofet/anduril.h new file mode 100644 index 0000000..b0a9960 --- /dev/null +++ b/hw/hank/emisar-d4v2/nofet/anduril.h @@ -0,0 +1,62 @@ +// Emisar D4v2-noFET config options for Anduril +// Copyright (C) 2020-2023 Selene ToyKeeper +// SPDX-License-Identifier: GPL-3.0-or-later +#pragma once + +// switch to 1-channel support functions +#define HWDEF_C_FILE hank/emisar-d4v2/nofet/hwdef.c + +#include "hank/emisar-d4v2/anduril.h" +#undef MODEL_NUMBER +#define MODEL_NUMBER "0115" +// ATTINY: 1634 + +// the ramp uses only 1x7135 chip, max ~130 lm +#undef PWM_CHANNELS +#define PWM_CHANNELS 1 + +#undef PWM1_LEVELS +#undef PWM2_LEVELS +#undef PWM_TOPS +//#define PWM1_LEVELS 1,1,1,2,2,2,2,3,3,3,3,4,4,5,5,6,6,6,7,8,8,9,9,10,10,11,12,13,13,14,15,16,16,17,18,19,20,21,22,23,23,24,26,27,28,29,30,31,32,33,34,36,37,38,39,41,42,43,45,46,47,49,50,52,53,55,56,58,59,61,62,64,66,67,69,71,72,74,76,78,80,81,83,85,87,89,91,93,95,97,99,101,103,105,107,109,111,113,116,118,120,122,125,127,129,132,134,136,139,141,144,146,148,151,154,156,159,161,164,166,169,172,174,177,180,183,185,188,191,194,197,200,203,205,208,211,214,217,220,223,226,230,233,236,239,242,245,249,252,255 +// level_calc.py 3.01 1 150 7135 -1 0.1 140 --pwm dyn:64:4096:255:3 --clock 11:21:8.0 +// (and some manual tweaks to make half/quarter speed levels less bumpy) +#define PWM1_LEVELS 1,1,2,2,3,4,4,5,6,7,9,10,11,11,12,13,13,14,15,15,18,18,17,18,18,19,19,19,19,19,20,20,20,20,19,19,19,19,19,19,19,19,19,19,19,19,19,19,19,19,19,20,20,20,21,21,22,23,24,24,26,27,28,29,30,31,32,33,34,35,36,38,39,40,42,43,44,46,47,49,50,52,53,55,56,58,60,62,63,65,67,69,71,73,75,77,79,81,83,85,88,90,92,95,97,100,102,105,107,110,112,115,118,121,124,127,129,132,135,139,142,145,148,151,155,158,162,165,169,172,176,179,183,187,191,195,199,203,207,211,215,219,223,228,232,237,241,246,250,255 +#define PWM_TOPS 4094,2719,3280,1954,2599,3032,2342,2548,2626,2635,2246,2261,2244,1964,1956,1929,1743,1733,1763,1697,1492,1362,1245,1231,1132,1118,1034,958,889,826,821,767,717,671,629,591,556,523,493,465,440,416,394,373,354,336,319,304,299,293,279,282,269,257,260,249,251,252,253,243,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 + +#undef MAX_1x7135 +#define MAX_1x7135 150 +#undef QUARTERSPEED_LEVEL +#undef HALFSPEED_LEVEL +#define QUARTERSPEED_LEVEL 11 +#define HALFSPEED_LEVEL 21 + +#undef DEFAULT_LEVEL +#define DEFAULT_LEVEL 80 + +#undef RAMP_SMOOTH_CEIL +#define RAMP_SMOOTH_CEIL 150 +// 10, 45, 80, 115, 150 +#undef RAMP_DISCRETE_FLOOR +#undef RAMP_DISCRETE_CEIL +#undef RAMP_DISCRETE_STEPS +#define RAMP_DISCRETE_FLOOR 10 +#define RAMP_DISCRETE_CEIL 150 +#define RAMP_DISCRETE_STEPS 5 + +// safe limit ~100% power because no FET +#undef SIMPLE_UI_FLOOR +#undef SIMPLE_UI_CEIL +#define SIMPLE_UI_FLOOR RAMP_DISCRETE_FLOOR +#define SIMPLE_UI_CEIL RAMP_DISCRETE_CEIL + +#undef CANDLE_AMPLITUDE +#define CANDLE_AMPLITUDE 60 + +#undef THERM_FASTER_LEVEL +#define THERM_FASTER_LEVEL 150 + +// maybe keep this, in case someone uses a higher power channel? +//#undef USE_THERMAL_REGULATION +//#undef USE_SET_LEVEL_GRADUALLY + diff --git a/hw/hank/emisar-d4v2/nofet/hwdef.c b/hw/hank/emisar-d4v2/nofet/hwdef.c new file mode 100644 index 0000000..971c06e --- /dev/null +++ b/hw/hank/emisar-d4v2/nofet/hwdef.c @@ -0,0 +1,55 @@ +// Emisar D4v2 (no DD FET, 1x7135 only) PWM helper functions +// Copyright (C) 2017-2023 Selene ToyKeeper +// SPDX-License-Identifier: GPL-3.0-or-later + +#pragma once + +#include "fsm/chan-rgbaux.c" + +void set_level_zero(); + +void set_level_main(uint8_t level); +bool gradual_tick_main(uint8_t gt); + + +Channel channels[] = { + { // main LEDs + .set_level = set_level_main, + .gradual_tick = gradual_tick_main + }, + RGB_AUX_CHANNELS +}; + + +void set_level_zero() { + CH1_PWM = 0; + PWM_CNT = 0; // reset phase +} + +// single set of LEDs with just a 1x7135 chip, max 350 mA or ~130 lm +void set_level_main(uint8_t level) { + PWM_DATATYPE ch1_pwm = PWM_GET(pwm1_levels, level); + // pulse frequency modulation, a.k.a. dynamic PWM + uint16_t top = PWM_GET16(pwm_tops, level); + + CH1_PWM = ch1_pwm; + // wait to sync the counter and avoid flashes + while(actual_level && (PWM_CNT > (top - 32))) {} + PWM_TOP = top; + // force reset phase when turning on from zero + // (because otherwise the initial response is inconsistent) + if (! actual_level) PWM_CNT = 0; +} + +bool gradual_tick_main(uint8_t gt) { + PWM_DATATYPE pwm1 = PWM_GET(pwm1_levels, gt); + + GRADUAL_ADJUST_SIMPLE (pwm1, CH1_PWM); + + if ( (pwm1 == CH1_PWM) + ) { + return true; // done + } + return false; // not done yet +} + diff --git a/hw/hank/noctigon-dm11-boost/anduril.h b/hw/hank/noctigon-dm11-boost/anduril.h deleted file mode 100644 index de6451f..0000000 --- a/hw/hank/noctigon-dm11-boost/anduril.h +++ /dev/null @@ -1,91 +0,0 @@ -// Noctigon DM11 (boost driver) config options for Anduril -// Copyright (C) 2021-2023 Selene ToyKeeper -// SPDX-License-Identifier: GPL-3.0-or-later -#pragma once - -#define MODEL_NUMBER "0273" -#include "hank/noctigon-dm11-boost/hwdef.h" -#include "hank/anduril.h" -// ATTINY: 1634 - -#define RAMP_SIZE 150 - -// power channels: -// - boost: 8A? -// - DD FET: none (can't do DD on a boost driver) - -#if 0 // old, dynamic PWM method -// level_calc.py 5.01 1 149 7135 1 0.3 1740 --pwm dyn:78:16384:255 -// (plus a 0 at the beginning for moon) -#define PWM1_LEVELS 0,1,1,1,2,3,3,4,5,6,7,8,9,10,11,13,14,16,17,19,21,23,25,27,29,31,34,36,39,42,44,47,50,53,57,60,63,67,70,74,77,81,85,88,92,96,99,103,107,110,113,117,120,123,126,128,130,133,134,136,137,137,137,137,136,135,133,130,126,122,117,111,104,96,87,76,65,52,38,22,23,25,26,27,28,29,30,32,33,34,36,37,39,40,42,43,45,47,49,51,53,55,57,59,61,63,66,68,70,73,76,78,81,84,87,90,93,96,99,103,106,110,113,117,121,125,129,133,137,142,146,151,155,160,165,170,175,181,186,192,197,203,209,215,222,228,234,241,248,255 -#define PWM_TOPS 16383,16383,12404,8140,11462,14700,11041,12947,13795,14111,14124,13946,13641,13248,12791,13418,12808,13057,12385,12428,12358,12209,12000,11746,11459,11147,11158,10793,10708,10576,10173,9998,9800,9585,9527,9278,9023,8901,8634,8486,8216,8053,7881,7615,7440,7261,7009,6832,6656,6422,6196,6031,5819,5615,5419,5190,4973,4803,4571,4386,4179,3955,3745,3549,3340,3145,2940,2729,2513,2312,2109,1903,1697,1491,1286,1070,871,662,459,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 -#define MAX_1x7135 150 -#define DEFAULT_LEVEL 70 -#define MIN_THERM_STEPDOWN 80 // must be > end of dynamic PWM range -#define HALFSPEED_LEVEL 12 -#define QUARTERSPEED_LEVEL 4 -#endif - -// delta-sigma modulated PWM (0b0HHHHHHHHLLLLLLL = 0, 8xHigh, 7xLow bits) -// level_calc.py 5.01 1 150 7135 0 0.2 2000 --pwm 32640 -// (max is (255 << 7), because it's 8-bit PWM plus 7 bits of DSM) -#define PWM1_LEVELS 0,1,2,3,4,5,6,7,9,10,12,14,17,19,22,25,28,32,36,41,45,50,56,62,69,76,84,92,101,110,121,132,143,156,169,184,199,215,232,251,270,291,313,336,360,386,414,442,473,505,539,574,612,651,693,736,782,829,880,932,987,1045,1105,1168,1233,1302,1374,1449,1527,1608,1693,1781,1873,1969,2068,2172,2279,2391,2507,2628,2753,2883,3018,3158,3303,3454,3609,3771,3938,4111,4289,4475,4666,4864,5068,5280,5498,5724,5957,6197,6445,6701,6965,7237,7518,7808,8106,8413,8730,9056,9392,9737,10093,10459,10835,11223,11621,12031,12452,12884,13329,13786,14255,14737,15232,15741,16262,16798,17347,17911,18489,19082,19691,20314,20954,21609,22281,22969,23674,24397,25137,25895,26671,27465,28279,29111,29963,30835,31727,32640 -#define MIN_THERM_STEPDOWN 50 -#define DEFAULT_LEVEL 70 -#define MAX_1x7135 150 -// always run at 1/4th speed, because 4 kHz PWM is enough for this circuit -// and speed changes make a big visible bump -#define HALFSPEED_LEVEL 255 -#define QUARTERSPEED_LEVEL 255 - -#define RAMP_SMOOTH_FLOOR 1 // low levels may be unreliable -#define RAMP_SMOOTH_CEIL 130 -// 10, 30, 50, [70], 90, 110, 130 -// Nichia B35 model: (0.56), 1.4, 8.4, 34.5, [102], 250, 500, 860, (1300) lm -#define RAMP_DISCRETE_FLOOR 10 -#define RAMP_DISCRETE_CEIL RAMP_SMOOTH_CEIL -#define RAMP_DISCRETE_STEPS 7 - -// safe limit ~75% power -#define SIMPLE_UI_FLOOR RAMP_DISCRETE_FLOOR -#define SIMPLE_UI_CEIL RAMP_DISCRETE_CEIL -#define SIMPLE_UI_STEPS 5 - -// stop panicking at ~70% power or ~600 lm -#define THERM_FASTER_LEVEL 130 - -#define THERM_CAL_OFFSET 5 - -// the power regulator seems to "jump start" the LEDs all on its own, -// so the firmware doesn't have to -// (and unfortunately the power regulator jumps it a bit too hard) -#define DEFAULT_JUMP_START_LEVEL 1 -#define BLINK_BRIGHTNESS 50 -#define BLINK_ONCE_TIME 12 - -// show each channel while it scroll by in the menu -#define USE_CONFIG_COLORS - -// blink numbers on the main LEDs by default (but allow user to change it) -#define DEFAULT_BLINK_CHANNEL CM_MAIN - -// slow down party strobe; this driver can't pulse for 2ms or less -#define PARTY_STROBE_ONTIME 3 - -// use aux red + aux blue for police strobe -#define USE_POLICE_COLOR_STROBE_MODE -#define POLICE_STROBE_USES_AUX -#define POLICE_COLOR_STROBE_CH1 CM_AUXRED -#define POLICE_COLOR_STROBE_CH2 CM_AUXBLU - -// the default of 26 looks a bit rough, so increase it to make it smoother -#define CANDLE_AMPLITUDE 33 - -// don't blink while ramping -#ifdef BLINK_AT_RAMP_MIDDLE -#undef BLINK_AT_RAMP_MIDDLE -#endif - -// added for convenience -#define USE_SOFT_FACTORY_RESET - diff --git a/hw/hank/noctigon-dm11-boost/hwdef.c b/hw/hank/noctigon-dm11-boost/hwdef.c deleted file mode 100644 index e601132..0000000 --- a/hw/hank/noctigon-dm11-boost/hwdef.c +++ /dev/null @@ -1,97 +0,0 @@ -// Noctigon DM11 (boost driver) PWM helper functions -// Copyright (C) 2023 Selene ToyKeeper -// SPDX-License-Identifier: GPL-3.0-or-later -#pragma once - -#include "fsm/chan-rgbaux.c" - - -void set_level_zero(); - -void set_level_main(uint8_t level); -bool gradual_tick_main(uint8_t gt); - - -Channel channels[] = { - { // channel 1 only - .set_level = set_level_main, - .gradual_tick = gradual_tick_main - }, - RGB_AUX_CHANNELS -}; - - -void set_level_zero() { - // disable timer overflow interrupt - // (helps improve button press handling from Off state) - DSM_INTCTRL &= ~DSM_OVF_bm; - - // turn off all LEDs - ch1_dsm_lvl = 0; - CH1_PWM = 0; - PWM_CNT = 0; // reset phase - CH1_ENABLE_PORT &= ~(1 << CH1_ENABLE_PIN ); // disable opamp - CH1_ENABLE_PORT2 &= ~(1 << CH1_ENABLE_PIN2); // disable PMIC -} - -// single set of LEDs with single power channel, boost -void set_level_main(uint8_t level) { - PWM_DATATYPE ch1 = PWM_GET(pwm1_levels, level); - - // set delta-sigma soft levels - ch1_dsm_lvl = ch1; - - // set hardware PWM levels and init dsm loop - CH1_PWM = ch1_pwm = ch1 >> 7; - - // enable timer overflow interrupt so DSM can work - DSM_INTCTRL |= DSM_OVF_bm; - - // force reset phase when turning on from zero - // (because otherwise the initial response is inconsistent) - if (! actual_level) PWM_CNT = 0; - - CH1_ENABLE_PORT |= (1 << CH1_ENABLE_PIN ); // enable opamp - CH1_ENABLE_PORT2 |= (1 << CH1_ENABLE_PIN2); // enable PMIC -} - -// delta-sigma modulation of PWM outputs -// happens on each Timer overflow (every 512 cpu clock cycles) -// uses 8-bit pwm w/ 7-bit dsm (0b 0PPP PPPP PDDD DDDD) -ISR(DSM_vect) { - // set new hardware values first, - // for best timing (reduce effect of interrupt jitter) - CH1_PWM = ch1_pwm; - - // calculate next values, now that timing matters less - - // accumulate error - ch1_dsm += (ch1_dsm_lvl & 0x007f); - // next PWM = base PWM value + carry bit - ch1_pwm = (ch1_dsm_lvl >> 7) + (ch1_dsm > 0x7f); - // clear carry bit - ch1_dsm &= 0x7f; -} - - -bool gradual_tick_main(uint8_t gt) { - PWM_DATATYPE ch1 = PWM_GET(pwm1_levels, gt); - - // adjust multiple times based on current brightness - // (so it adjusts faster/coarser when bright, slower/finer when dim) - - // higher shift = slower/finer adjustments - const uint8_t shift = 9; // ((255 << 7) >> 9) = 63 max - uint8_t steps; - - steps = ch1_dsm_lvl >> shift; - for (uint8_t i=0; i<=steps; i++) - GRADUAL_ADJUST_SIMPLE(ch1, ch1_dsm_lvl); - - if ((ch1 == ch1_dsm_lvl) - ) { - return true; // done - } - return false; // not done yet -} - diff --git a/hw/hank/noctigon-dm11-boost/hwdef.h b/hw/hank/noctigon-dm11-boost/hwdef.h deleted file mode 100644 index dffd462..0000000 --- a/hw/hank/noctigon-dm11-boost/hwdef.h +++ /dev/null @@ -1,206 +0,0 @@ -// Noctigon DM11 boost driver layout (attiny1634) -// Copyright (C) 2021-2023 Selene ToyKeeper -// SPDX-License-Identifier: GPL-3.0-or-later -#pragma once - -/* - * (based on Noctigon K1) - * - * Pin / Name / Function - * 1 PA6 (none) (PWM1B) (reserved for DD drivers) - * 2 PA5 R: red aux LED (PWM0B) - * 3 PA4 G: green aux LED - * 4 PA3 B: blue aux LED - * 5 PA2 L: button LED - * 6 PA1 (none) - * 7 PA0 (none) - * 8 GND GND - * 9 VCC VCC - * 10 PC5 (none) - * 11 PC4 (none) - * 12 PC3 RESET - * 13 PC2 (none) - * 14 PC1 SCK - * 15 PC0 boost PMIC enable (PWM0A not used) - * 16 PB3 main LED PWM (PWM1A) - * 17 PB2 MISO (PCINT10) - * 18 PB1 MOSI / battery voltage (ADC6) - * 19 PB0 Opamp power - * 20 PA7 e-switch (PCINT7) - * ADC12 thermal sensor - * - * Main LED power uses one pin to turn the Opamp on/off, - * and one pin to control Opamp power level. - * Regulated brightness control uses the power level pin, with PWM+DSM. - * The on/off pin is only used to turn the main LED on and off, - * not to change brightness. - */ - -#define ATTINY 1634 -#include - -#define HWDEF_C_FILE hank/noctigon-dm11-boost/hwdef.c - -// allow using aux LEDs as extra channel modes -#include "fsm/chan-rgbaux.h" - -// channel modes: -// * 0. main LEDs -// * 1+. aux RGB -#define NUM_CHANNEL_MODES (1 + NUM_RGB_AUX_CHANNEL_MODES) -enum CHANNEL_MODES { - CM_MAIN = 0, - RGB_AUX_ENUMS -}; - -#define DEFAULT_CHANNEL_MODE CM_MAIN - -// right-most bit first, modes are in fedcba9876543210 order -#define CHANNEL_MODES_ENABLED 0b0000000000000001 -// no args -//#define USE_CHANNEL_MODE_ARGS -//#define CHANNEL_MODE_ARGS 0,0,0,0,0,0,0,0 - - -#define PWM_CHANNELS 1 // old, remove this - -#define PWM_BITS 16 // 0 to 32640 (0 to 255 PWM + 0 to 127 DSM) at constant kHz -#define PWM_GET PWM_GET16 -#define PWM_DATATYPE uint16_t -#define PWM_DATATYPE2 uint32_t // only needs 32-bit if ramp values go over 255 -#define PWM1_DATATYPE uint16_t // 15-bit PWM+DSM ramp - -#define PWM_TOP ICR1 // holds the TOP value for variable-resolution PWM -#define PWM_TOP_INIT 255 -#define PWM_CNT TCNT1 // for checking / resetting phase -// (max is (255 << 7), because it's 8-bit PWM plus 7 bits of DSM) -#define DSM_TOP (255<<7) // 15-bit resolution leaves 1 bit for carry - -// timer interrupt for DSM -#define DSM_vect TIMER1_OVF_vect -#define DSM_INTCTRL TIMSK -#define DSM_OVF_bm (1< end of dynamic PWM range - diff --git a/hw/hank/noctigon-dm11-sbt90/anduril.h b/hw/hank/noctigon-dm11-sbt90/anduril.h deleted file mode 100644 index 8c0d1de..0000000 --- a/hw/hank/noctigon-dm11-sbt90/anduril.h +++ /dev/null @@ -1,46 +0,0 @@ -// Noctigon DM11-SBT90.2 config options for Anduril -// Copyright (C) 2021-2023 Selene ToyKeeper -// SPDX-License-Identifier: GPL-3.0-or-later -#pragma once - -#include "hank/noctigon-kr4/anduril.h" -#undef MODEL_NUMBER -#define MODEL_NUMBER "0274" -// ATTINY: 1634 - -// this light has three aux LED channels: R, G, B -#define USE_AUX_RGB_LEDS -// ... and a single LED in the button -#define USE_BUTTON_LED -// don't use aux LEDs while main LED is on -#ifdef USE_INDICATOR_LED_WHILE_RAMPING -#undef USE_INDICATOR_LED_WHILE_RAMPING -#endif - -// power channels: -// - linear: 5A? -// - FET: DD - -#undef DEFAULT_LEVEL -#define DEFAULT_LEVEL 70 - -#undef RAMP_SMOOTH_FLOOR -#define RAMP_SMOOTH_FLOOR 10 // low levels may be unreliable -// 10, 30, 50, [70], 90, 110, 130 -#undef RAMP_DISCRETE_FLOOR -#define RAMP_DISCRETE_FLOOR 10 - -// safe limit ~75% power -#undef SIMPLE_UI_CEIL -#define SIMPLE_UI_CEIL RAMP_DISCRETE_CEIL - -// stop panicking at ~70% power or ~600 lm -#undef THERM_FASTER_LEVEL -#define THERM_FASTER_LEVEL 130 - -#undef BLINK_BRIGHTNESS -#define BLINK_BRIGHTNESS 50 - -#undef CANDLE_AMPLITUDE -#define CANDLE_AMPLITUDE 30 - diff --git a/hw/hank/noctigon-dm11/boost/anduril.h b/hw/hank/noctigon-dm11/boost/anduril.h new file mode 100644 index 0000000..7b62173 --- /dev/null +++ b/hw/hank/noctigon-dm11/boost/anduril.h @@ -0,0 +1,91 @@ +// Noctigon DM11 (boost driver) config options for Anduril +// Copyright (C) 2021-2023 Selene ToyKeeper +// SPDX-License-Identifier: GPL-3.0-or-later +#pragma once + +#define MODEL_NUMBER "0273" +#include "hank/noctigon-dm11/boost/hwdef.h" +#include "hank/anduril.h" +// ATTINY: 1634 + +#define RAMP_SIZE 150 + +// power channels: +// - boost: 8A? +// - DD FET: none (can't do DD on a boost driver) + +#if 0 // old, dynamic PWM method +// level_calc.py 5.01 1 149 7135 1 0.3 1740 --pwm dyn:78:16384:255 +// (plus a 0 at the beginning for moon) +#define PWM1_LEVELS 0,1,1,1,2,3,3,4,5,6,7,8,9,10,11,13,14,16,17,19,21,23,25,27,29,31,34,36,39,42,44,47,50,53,57,60,63,67,70,74,77,81,85,88,92,96,99,103,107,110,113,117,120,123,126,128,130,133,134,136,137,137,137,137,136,135,133,130,126,122,117,111,104,96,87,76,65,52,38,22,23,25,26,27,28,29,30,32,33,34,36,37,39,40,42,43,45,47,49,51,53,55,57,59,61,63,66,68,70,73,76,78,81,84,87,90,93,96,99,103,106,110,113,117,121,125,129,133,137,142,146,151,155,160,165,170,175,181,186,192,197,203,209,215,222,228,234,241,248,255 +#define PWM_TOPS 16383,16383,12404,8140,11462,14700,11041,12947,13795,14111,14124,13946,13641,13248,12791,13418,12808,13057,12385,12428,12358,12209,12000,11746,11459,11147,11158,10793,10708,10576,10173,9998,9800,9585,9527,9278,9023,8901,8634,8486,8216,8053,7881,7615,7440,7261,7009,6832,6656,6422,6196,6031,5819,5615,5419,5190,4973,4803,4571,4386,4179,3955,3745,3549,3340,3145,2940,2729,2513,2312,2109,1903,1697,1491,1286,1070,871,662,459,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 +#define MAX_1x7135 150 +#define DEFAULT_LEVEL 70 +#define MIN_THERM_STEPDOWN 80 // must be > end of dynamic PWM range +#define HALFSPEED_LEVEL 12 +#define QUARTERSPEED_LEVEL 4 +#endif + +// delta-sigma modulated PWM (0b0HHHHHHHHLLLLLLL = 0, 8xHigh, 7xLow bits) +// level_calc.py 5.01 1 150 7135 0 0.2 2000 --pwm 32640 +// (max is (255 << 7), because it's 8-bit PWM plus 7 bits of DSM) +#define PWM1_LEVELS 0,1,2,3,4,5,6,7,9,10,12,14,17,19,22,25,28,32,36,41,45,50,56,62,69,76,84,92,101,110,121,132,143,156,169,184,199,215,232,251,270,291,313,336,360,386,414,442,473,505,539,574,612,651,693,736,782,829,880,932,987,1045,1105,1168,1233,1302,1374,1449,1527,1608,1693,1781,1873,1969,2068,2172,2279,2391,2507,2628,2753,2883,3018,3158,3303,3454,3609,3771,3938,4111,4289,4475,4666,4864,5068,5280,5498,5724,5957,6197,6445,6701,6965,7237,7518,7808,8106,8413,8730,9056,9392,9737,10093,10459,10835,11223,11621,12031,12452,12884,13329,13786,14255,14737,15232,15741,16262,16798,17347,17911,18489,19082,19691,20314,20954,21609,22281,22969,23674,24397,25137,25895,26671,27465,28279,29111,29963,30835,31727,32640 +#define MIN_THERM_STEPDOWN 50 +#define DEFAULT_LEVEL 70 +#define MAX_1x7135 150 +// always run at 1/4th speed, because 4 kHz PWM is enough for this circuit +// and speed changes make a big visible bump +#define HALFSPEED_LEVEL 255 +#define QUARTERSPEED_LEVEL 255 + +#define RAMP_SMOOTH_FLOOR 1 // low levels may be unreliable +#define RAMP_SMOOTH_CEIL 130 +// 10, 30, 50, [70], 90, 110, 130 +// Nichia B35 model: (0.56), 1.4, 8.4, 34.5, [102], 250, 500, 860, (1300) lm +#define RAMP_DISCRETE_FLOOR 10 +#define RAMP_DISCRETE_CEIL RAMP_SMOOTH_CEIL +#define RAMP_DISCRETE_STEPS 7 + +// safe limit ~75% power +#define SIMPLE_UI_FLOOR RAMP_DISCRETE_FLOOR +#define SIMPLE_UI_CEIL RAMP_DISCRETE_CEIL +#define SIMPLE_UI_STEPS 5 + +// stop panicking at ~70% power or ~600 lm +#define THERM_FASTER_LEVEL 130 + +#define THERM_CAL_OFFSET 5 + +// the power regulator seems to "jump start" the LEDs all on its own, +// so the firmware doesn't have to +// (and unfortunately the power regulator jumps it a bit too hard) +#define DEFAULT_JUMP_START_LEVEL 1 +#define BLINK_BRIGHTNESS 50 +#define BLINK_ONCE_TIME 12 + +// show each channel while it scroll by in the menu +#define USE_CONFIG_COLORS + +// blink numbers on the main LEDs by default (but allow user to change it) +#define DEFAULT_BLINK_CHANNEL CM_MAIN + +// slow down party strobe; this driver can't pulse for 2ms or less +#define PARTY_STROBE_ONTIME 3 + +// use aux red + aux blue for police strobe +#define USE_POLICE_COLOR_STROBE_MODE +#define POLICE_STROBE_USES_AUX +#define POLICE_COLOR_STROBE_CH1 CM_AUXRED +#define POLICE_COLOR_STROBE_CH2 CM_AUXBLU + +// the default of 26 looks a bit rough, so increase it to make it smoother +#define CANDLE_AMPLITUDE 33 + +// don't blink while ramping +#ifdef BLINK_AT_RAMP_MIDDLE +#undef BLINK_AT_RAMP_MIDDLE +#endif + +// added for convenience +#define USE_SOFT_FACTORY_RESET + diff --git a/hw/hank/noctigon-dm11/boost/hwdef.c b/hw/hank/noctigon-dm11/boost/hwdef.c new file mode 100644 index 0000000..e601132 --- /dev/null +++ b/hw/hank/noctigon-dm11/boost/hwdef.c @@ -0,0 +1,97 @@ +// Noctigon DM11 (boost driver) PWM helper functions +// Copyright (C) 2023 Selene ToyKeeper +// SPDX-License-Identifier: GPL-3.0-or-later +#pragma once + +#include "fsm/chan-rgbaux.c" + + +void set_level_zero(); + +void set_level_main(uint8_t level); +bool gradual_tick_main(uint8_t gt); + + +Channel channels[] = { + { // channel 1 only + .set_level = set_level_main, + .gradual_tick = gradual_tick_main + }, + RGB_AUX_CHANNELS +}; + + +void set_level_zero() { + // disable timer overflow interrupt + // (helps improve button press handling from Off state) + DSM_INTCTRL &= ~DSM_OVF_bm; + + // turn off all LEDs + ch1_dsm_lvl = 0; + CH1_PWM = 0; + PWM_CNT = 0; // reset phase + CH1_ENABLE_PORT &= ~(1 << CH1_ENABLE_PIN ); // disable opamp + CH1_ENABLE_PORT2 &= ~(1 << CH1_ENABLE_PIN2); // disable PMIC +} + +// single set of LEDs with single power channel, boost +void set_level_main(uint8_t level) { + PWM_DATATYPE ch1 = PWM_GET(pwm1_levels, level); + + // set delta-sigma soft levels + ch1_dsm_lvl = ch1; + + // set hardware PWM levels and init dsm loop + CH1_PWM = ch1_pwm = ch1 >> 7; + + // enable timer overflow interrupt so DSM can work + DSM_INTCTRL |= DSM_OVF_bm; + + // force reset phase when turning on from zero + // (because otherwise the initial response is inconsistent) + if (! actual_level) PWM_CNT = 0; + + CH1_ENABLE_PORT |= (1 << CH1_ENABLE_PIN ); // enable opamp + CH1_ENABLE_PORT2 |= (1 << CH1_ENABLE_PIN2); // enable PMIC +} + +// delta-sigma modulation of PWM outputs +// happens on each Timer overflow (every 512 cpu clock cycles) +// uses 8-bit pwm w/ 7-bit dsm (0b 0PPP PPPP PDDD DDDD) +ISR(DSM_vect) { + // set new hardware values first, + // for best timing (reduce effect of interrupt jitter) + CH1_PWM = ch1_pwm; + + // calculate next values, now that timing matters less + + // accumulate error + ch1_dsm += (ch1_dsm_lvl & 0x007f); + // next PWM = base PWM value + carry bit + ch1_pwm = (ch1_dsm_lvl >> 7) + (ch1_dsm > 0x7f); + // clear carry bit + ch1_dsm &= 0x7f; +} + + +bool gradual_tick_main(uint8_t gt) { + PWM_DATATYPE ch1 = PWM_GET(pwm1_levels, gt); + + // adjust multiple times based on current brightness + // (so it adjusts faster/coarser when bright, slower/finer when dim) + + // higher shift = slower/finer adjustments + const uint8_t shift = 9; // ((255 << 7) >> 9) = 63 max + uint8_t steps; + + steps = ch1_dsm_lvl >> shift; + for (uint8_t i=0; i<=steps; i++) + GRADUAL_ADJUST_SIMPLE(ch1, ch1_dsm_lvl); + + if ((ch1 == ch1_dsm_lvl) + ) { + return true; // done + } + return false; // not done yet +} + diff --git a/hw/hank/noctigon-dm11/boost/hwdef.h b/hw/hank/noctigon-dm11/boost/hwdef.h new file mode 100644 index 0000000..513d32f --- /dev/null +++ b/hw/hank/noctigon-dm11/boost/hwdef.h @@ -0,0 +1,206 @@ +// Noctigon DM11 boost driver layout (attiny1634) +// Copyright (C) 2021-2023 Selene ToyKeeper +// SPDX-License-Identifier: GPL-3.0-or-later +#pragma once + +/* + * (based on Noctigon K1) + * + * Pin / Name / Function + * 1 PA6 (none) (PWM1B) (reserved for DD drivers) + * 2 PA5 R: red aux LED (PWM0B) + * 3 PA4 G: green aux LED + * 4 PA3 B: blue aux LED + * 5 PA2 L: button LED + * 6 PA1 (none) + * 7 PA0 (none) + * 8 GND GND + * 9 VCC VCC + * 10 PC5 (none) + * 11 PC4 (none) + * 12 PC3 RESET + * 13 PC2 (none) + * 14 PC1 SCK + * 15 PC0 boost PMIC enable (PWM0A not used) + * 16 PB3 main LED PWM (PWM1A) + * 17 PB2 MISO (PCINT10) + * 18 PB1 MOSI / battery voltage (ADC6) + * 19 PB0 Opamp power + * 20 PA7 e-switch (PCINT7) + * ADC12 thermal sensor + * + * Main LED power uses one pin to turn the Opamp on/off, + * and one pin to control Opamp power level. + * Regulated brightness control uses the power level pin, with PWM+DSM. + * The on/off pin is only used to turn the main LED on and off, + * not to change brightness. + */ + +#define ATTINY 1634 +#include + +#define HWDEF_C_FILE hank/noctigon-dm11/boost/hwdef.c + +// allow using aux LEDs as extra channel modes +#include "fsm/chan-rgbaux.h" + +// channel modes: +// * 0. main LEDs +// * 1+. aux RGB +#define NUM_CHANNEL_MODES (1 + NUM_RGB_AUX_CHANNEL_MODES) +enum CHANNEL_MODES { + CM_MAIN = 0, + RGB_AUX_ENUMS +}; + +#define DEFAULT_CHANNEL_MODE CM_MAIN + +// right-most bit first, modes are in fedcba9876543210 order +#define CHANNEL_MODES_ENABLED 0b0000000000000001 +// no args +//#define USE_CHANNEL_MODE_ARGS +//#define CHANNEL_MODE_ARGS 0,0,0,0,0,0,0,0 + + +#define PWM_CHANNELS 1 // old, remove this + +#define PWM_BITS 16 // 0 to 32640 (0 to 255 PWM + 0 to 127 DSM) at constant kHz +#define PWM_GET PWM_GET16 +#define PWM_DATATYPE uint16_t +#define PWM_DATATYPE2 uint32_t // only needs 32-bit if ramp values go over 255 +#define PWM1_DATATYPE uint16_t // 15-bit PWM+DSM ramp + +#define PWM_TOP ICR1 // holds the TOP value for variable-resolution PWM +#define PWM_TOP_INIT 255 +#define PWM_CNT TCNT1 // for checking / resetting phase +// (max is (255 << 7), because it's 8-bit PWM plus 7 bits of DSM) +#define DSM_TOP (255<<7) // 15-bit resolution leaves 1 bit for carry + +// timer interrupt for DSM +#define DSM_vect TIMER1_OVF_vect +#define DSM_INTCTRL TIMSK +#define DSM_OVF_bm (1< end of dynamic PWM range + diff --git a/hw/hank/noctigon-dm11/sbt90/anduril.h b/hw/hank/noctigon-dm11/sbt90/anduril.h new file mode 100644 index 0000000..8c0d1de --- /dev/null +++ b/hw/hank/noctigon-dm11/sbt90/anduril.h @@ -0,0 +1,46 @@ +// Noctigon DM11-SBT90.2 config options for Anduril +// Copyright (C) 2021-2023 Selene ToyKeeper +// SPDX-License-Identifier: GPL-3.0-or-later +#pragma once + +#include "hank/noctigon-kr4/anduril.h" +#undef MODEL_NUMBER +#define MODEL_NUMBER "0274" +// ATTINY: 1634 + +// this light has three aux LED channels: R, G, B +#define USE_AUX_RGB_LEDS +// ... and a single LED in the button +#define USE_BUTTON_LED +// don't use aux LEDs while main LED is on +#ifdef USE_INDICATOR_LED_WHILE_RAMPING +#undef USE_INDICATOR_LED_WHILE_RAMPING +#endif + +// power channels: +// - linear: 5A? +// - FET: DD + +#undef DEFAULT_LEVEL +#define DEFAULT_LEVEL 70 + +#undef RAMP_SMOOTH_FLOOR +#define RAMP_SMOOTH_FLOOR 10 // low levels may be unreliable +// 10, 30, 50, [70], 90, 110, 130 +#undef RAMP_DISCRETE_FLOOR +#define RAMP_DISCRETE_FLOOR 10 + +// safe limit ~75% power +#undef SIMPLE_UI_CEIL +#define SIMPLE_UI_CEIL RAMP_DISCRETE_CEIL + +// stop panicking at ~70% power or ~600 lm +#undef THERM_FASTER_LEVEL +#define THERM_FASTER_LEVEL 130 + +#undef BLINK_BRIGHTNESS +#define BLINK_BRIGHTNESS 50 + +#undef CANDLE_AMPLITUDE +#define CANDLE_AMPLITUDE 30 + diff --git a/hw/hank/noctigon-k1-boost/anduril.h b/hw/hank/noctigon-k1-boost/anduril.h deleted file mode 100644 index e18a015..0000000 --- a/hw/hank/noctigon-k1-boost/anduril.h +++ /dev/null @@ -1,96 +0,0 @@ -// Noctigon K1 boost config options for Anduril -// Copyright (C) 2019-2023 Selene ToyKeeper -// SPDX-License-Identifier: GPL-3.0-or-later -#pragma once - -#define MODEL_NUMBER "0253" -#include "hank/noctigon-k1-boost/hwdef.h" -#include "hank/anduril.h" -// ATTINY: 1634 - -// Most K1 lights can run hotter than default, but the 12V model -// is known to have issues with the driver itself getting too hot. -// This then causes the main LEDs to turn off during use, because the -// boost chip's built-in protection activates. So try to keep the -// temperature relatively low. -#undef DEFAULT_THERM_CEIL -#define DEFAULT_THERM_CEIL 45 - -// this light has three aux LED channels: R, G, B -#define USE_AUX_RGB_LEDS -#define USE_AUX_RGB_LEDS_WHILE_ON 25 -#define USE_INDICATOR_LED_WHILE_RAMPING - -#if 0 // old, 10-bit PWM method -// level_calc.py cube 1 150 7135 0 4 1300 -// (with max_pwm set to 1023) -// (level 0 is usable on this light) -#define RAMP_LENGTH 150 -#define PWM1_LEVELS 0,0,1,1,2,2,3,3,4,5,5,6,7,8,9,10,11,12,13,14,15,16,17,19,20,22,23,25,26,28,30,31,33,35,37,39,42,44,46,48,51,53,56,59,61,64,67,70,73,76,80,83,86,90,94,97,101,105,109,113,117,122,126,130,135,140,144,149,154,159,165,170,175,181,187,193,198,204,211,217,223,230,236,243,250,257,264,271,279,286,294,302,310,318,326,334,343,351,360,369,378,387,397,406,416,426,436,446,456,466,477,488,499,510,521,532,544,555,567,579,591,604,616,629,642,655,668,682,695,709,723,737,751,766,780,795,810,825,841,856,872,888,904,921,937,954,971,988,1005,1023 -#define MAX_1x7135 50 -// don't slow down at low levels; this isn't that sort of light -// (it needs to stay at full speed for the 10-bit PWM to work) -#ifdef USE_DYNAMIC_UNDERCLOCKING -#undef USE_DYNAMIC_UNDERCLOCKING -#endif -#endif - -#define RAMP_SIZE 150 -// delta-sigma modulated PWM (0b0HHHHHHHHLLLLLLL = 0, 8xHigh, 7xLow bits) -// level_calc.py 5.01 1 150 7135 0 0.2 2000 --pwm 32640 -// (max is (255 << 7), because it's 8-bit PWM plus 7 bits of DSM) -#define PWM1_LEVELS 0,1,2,3,4,5,6,7,9,10,12,14,17,19,22,25,28,32,36,41,45,50,56,62,69,76,84,92,101,110,121,132,143,156,169,184,199,215,232,251,270,291,313,336,360,386,414,442,473,505,539,574,612,651,693,736,782,829,880,932,987,1045,1105,1168,1233,1302,1374,1449,1527,1608,1693,1781,1873,1969,2068,2172,2279,2391,2507,2628,2753,2883,3018,3158,3303,3454,3609,3771,3938,4111,4289,4475,4666,4864,5068,5280,5498,5724,5957,6197,6445,6701,6965,7237,7518,7808,8106,8413,8730,9056,9392,9737,10093,10459,10835,11223,11621,12031,12452,12884,13329,13786,14255,14737,15232,15741,16262,16798,17347,17911,18489,19082,19691,20314,20954,21609,22281,22969,23674,24397,25137,25895,26671,27465,28279,29111,29963,30835,31727,32640 -#define MIN_THERM_STEPDOWN 50 -#define DEFAULT_LEVEL 70 -#define MAX_1x7135 150 -// always run at 1/4th speed, because 4 kHz PWM is enough for this circuit -// and speed changes make a big visible bump -#define HALFSPEED_LEVEL 255 -#define QUARTERSPEED_LEVEL 255 - -#define RAMP_SMOOTH_FLOOR 1 -#define RAMP_SMOOTH_CEIL 130 -// 10, 30, 50, [70], 90, 110, 130 -#define RAMP_DISCRETE_FLOOR 10 -#define RAMP_DISCRETE_CEIL RAMP_SMOOTH_CEIL -#define RAMP_DISCRETE_STEPS 7 - -// safe limit ~50% power -#define SIMPLE_UI_FLOOR RAMP_DISCRETE_FLOOR -#define SIMPLE_UI_CEIL 120 -#define SIMPLE_UI_STEPS 5 - -// stop panicking at ~70% power or ~600 lm -#define THERM_FASTER_LEVEL 130 - -#define THERM_CAL_OFFSET 5 - -#define THERM_RESPONSE_MAGNITUDE 32 // smaller adjustments, this host changes temperature slowly -#define THERM_NEXT_WARNING_THRESHOLD 32 // more error tolerance before adjusting - -// show each channel while it scroll by in the menu -#define USE_CONFIG_COLORS - -// blink numbers on the main LEDs by default (but allow user to change it) -#define DEFAULT_BLINK_CHANNEL CM_MAIN - -// slow down party strobe; this driver can't pulse for 1ms or less -#define PARTY_STROBE_ONTIME 4 - -// use aux red + aux blue for police strobe -#define USE_POLICE_COLOR_STROBE_MODE -#define POLICE_STROBE_USES_AUX -#define POLICE_COLOR_STROBE_CH1 CM_AUXRED -#define POLICE_COLOR_STROBE_CH2 CM_AUXBLU - -// make candle mode wobble more -#define CANDLE_AMPLITUDE 33 - -// the entire ramp is regulated; don't blink halfway up -#ifdef BLINK_AT_RAMP_MIDDLE -#undef BLINK_AT_RAMP_MIDDLE -#endif - -// added for convenience -#define USE_SOFT_FACTORY_RESET - diff --git a/hw/hank/noctigon-k1-boost/hwdef.h b/hw/hank/noctigon-k1-boost/hwdef.h deleted file mode 100644 index 1c6a06d..0000000 --- a/hw/hank/noctigon-k1-boost/hwdef.h +++ /dev/null @@ -1,188 +0,0 @@ -// Noctigon K1 12V driver layout (attiny1634) -// Copyright (C) 2019-2023 Selene ToyKeeper -// SPDX-License-Identifier: GPL-3.0-or-later -#pragma once - -/* - * Pin / Name / Function - * 1 PA6 (none) (PWM1B) (reserved for DD drivers) - * 2 PA5 R: red aux LED (PWM0B) - * 3 PA4 G: green aux LED - * 4 PA3 B: blue aux LED - * 5 PA2 (none) (reserved for L: button LED (on some models)) - * 6 PA1 (none) - * 7 PA0 (none) - * 8 GND GND - * 9 VCC VCC - * 10 PC5 (none) - * 11 PC4 (none) - * 12 PC3 RESET - * 13 PC2 (none) - * 14 PC1 SCK - * 15 PC0 boost PMIC enable (PWM0A not used) - * 16 PB3 main LED PWM (PWM1A) - * 17 PB2 MISO - * 18 PB1 MOSI / battery voltage (ADC6) - * 19 PB0 Opamp power - * 20 PA7 e-switch (PCINT7) - * ADC12 thermal sensor - * - * Main LED power uses one pin to turn the Opamp on/off, - * and one pin to control Opamp power level. - * Regulated brightness control uses the power level pin, with PWM+DSM. - * The on/off pin is only used to turn the main LED on and off, - * not to change brightness. - */ - -#define ATTINY 1634 -#include - -#define HWDEF_C_FILE hank/noctigon-dm11-boost/hwdef.c - -// allow using aux LEDs as extra channel modes -#include "fsm/chan-rgbaux.h" - -// channel modes: -// * 0. main LEDs -// * 1+. aux RGB -#define NUM_CHANNEL_MODES (1 + NUM_RGB_AUX_CHANNEL_MODES) -enum CHANNEL_MODES { - CM_MAIN = 0, - RGB_AUX_ENUMS -}; - -#define DEFAULT_CHANNEL_MODE CM_MAIN - -// right-most bit first, modes are in fedcba9876543210 order -#define CHANNEL_MODES_ENABLED 0b0000000000000001 -// no args -//#define USE_CHANNEL_MODE_ARGS -//#define CHANNEL_MODE_ARGS 0,0,0,0,0,0,0,0 - - -#define PWM_CHANNELS 1 // old, remove this - -#define PWM_BITS 16 // 0 to 32640 (0 to 255 PWM + 0 to 127 DSM) at constant kHz -#define PWM_GET PWM_GET16 -#define PWM_DATATYPE uint16_t -#define PWM_DATATYPE2 uint32_t // only needs 32-bit if ramp values go over 255 -#define PWM1_DATATYPE uint16_t // 15-bit PWM+DSM ramp - -#define PWM_TOP ICR1 // holds the TOP value for variable-resolution PWM -#define PWM_TOP_INIT 255 -#define PWM_CNT TCNT1 // for checking / resetting phase -// (max is (255 << 7), because it's 8-bit PWM plus 7 bits of DSM) -#define DSM_TOP (255<<7) // 15-bit resolution leaves 1 bit for carry - -// timer interrupt for DSM -#define DSM_vect TIMER1_OVF_vect -#define DSM_INTCTRL TIMSK -#define DSM_OVF_bm (1< - -#define HWDEF_C_FILE hank/noctigon-kr4/hwdef.c - -// allow using aux LEDs as extra channel modes -#include "fsm/chan-rgbaux.h" - -// channel modes: -// * 0. linear + DD FET stacked -// * 1+. aux RGB -#define NUM_CHANNEL_MODES (1 + NUM_RGB_AUX_CHANNEL_MODES) -enum CHANNEL_MODES { - CM_MAIN = 0, - RGB_AUX_ENUMS -}; - -#define DEFAULT_CHANNEL_MODE CM_MAIN - -// right-most bit first, modes are in fedcba9876543210 order -#define CHANNEL_MODES_ENABLED 0b0000000000000001 -// no args -//#define USE_CHANNEL_MODE_ARGS -//#define CHANNEL_MODE_ARGS 0,0,0,0,0,0,0,0 - - -#define PWM_CHANNELS 2 // old, remove this - -#define PWM_BITS 16 // dynamic 16-bit, but never goes over 255 -#define PWM_GET PWM_GET8 -#define PWM_DATATYPE uint16_t // is used for PWM_TOPS (which goes way over 255) -#define PWM_DATATYPE2 uint16_t // only needs 32-bit if ramp values go over 255 -#define PWM1_DATATYPE uint8_t // linear ramp -#define PWM2_DATATYPE uint8_t // DD FET ramp - -// PWM parameters of both channels are tied together because they share a counter -#define PWM_TOP ICR1 // holds the TOP value for variable-resolution PWM -#define PWM_TOP_INIT 255 // highest value used in top half of ramp -#define PWM_CNT TCNT1 // for dynamic PWM, reset phase - -// linear channel -#define CH1_PIN PB3 // pin 16, Opamp reference -#define CH1_PWM OCR1A // OCR1A is the output compare register for PB3 -#define CH1_ENABLE_PIN PB0 // pin 19, Opamp power -#define CH1_ENABLE_PORT PORTB // control port for PB0 - -// DD FET channel -#define CH2_PIN PA6 // pin 1, DD FET PWM -#define CH2_PWM OCR1B // OCR1B is the output compare register for PA6 - -// e-switch -#define SWITCH_PIN PB2 // pin 17 -#define SWITCH_PCINT PCINT10 // pin 17 pin change interrupt -#define SWITCH_PCIE PCIE1 // PCIE1 is for PCINT[11:8] -#define SWITCH_PCMSK PCMSK1 // PCMSK1 is for PCINT[11:8] -#define SWITCH_PORT PINB // PINA or PINB or PINC -#define SWITCH_PUE PUEB // pullup group B -#define PCINT_vect PCINT1_vect // ISR for PCINT[11:8] - -#define USE_VOLTAGE_DIVIDER // use a dedicated pin, not VCC, because VCC input is flattened -#define VOLTAGE_PIN PB1 // Pin 18 / PB1 / ADC6 -// pin to ADC mappings are in DS table 19-4 -#define VOLTAGE_ADC ADC6D // digital input disable pin for PB1 -// DIDR0/DIDR1 mappings are in DS section 19.13.5, 19.13.6 -#define VOLTAGE_ADC_DIDR DIDR1 // DIDR channel for ADC6D -// DS tables 19-3, 19-4 -// Bit 7 6 5 4 3 2 1 0 -// REFS1 REFS0 REFEN ADC0EN MUX3 MUX2 MUX1 MUX0 -// MUX[3:0] = 0, 1, 1, 0 for ADC6 / PB1 -// divided by ... -// REFS[1:0] = 1, 0 for internal 1.1V reference -// other bits reserved -#define ADMUX_VOLTAGE_DIVIDER 0b10000110 -#define ADC_PRSCL 0x07 // clk/128 - -// TODO: calibrate this -// Raw ADC readings at 4.4V and 2.2V -// calibrate the voltage readout here -// estimated / calculated values are: -// (voltage - D1) * (R2/(R2+R1) * 1024 / 1.1) -// D1, R1, R2 = 0, 330, 100 -#ifndef ADC_44 -//#define ADC_44 981 // raw value at 4.40V -#define ADC_44 967 // manually tweaked so 4.16V will blink out 4.2 -#endif -#ifndef ADC_22 -//#define ADC_22 489 // raw value at 2.20V -#define ADC_22 482 // manually tweaked so 4.16V will blink out 4.2 -#endif - -#define TEMP_CHANNEL 0b00001111 - -// this light has aux LEDs under the optic -#define AUXLED_R_PIN PA5 // pin 2 -#define AUXLED_G_PIN PA4 // pin 3 -#define AUXLED_B_PIN PA3 // pin 4 -#define AUXLED_RGB_PORT PORTA // PORTA or PORTB or PORTC -#define AUXLED_RGB_DDR DDRA // DDRA or DDRB or DDRC -#define AUXLED_RGB_PUE PUEA // PUEA or PUEB or PUEC - -inline void hwdef_setup() { - // enable output ports - // Opamp level and Opamp on/off - DDRB = (1 << CH1_PIN) - | (1 << CH1_ENABLE_PIN); - // DD FET PWM, aux R/G/B - DDRA = (1 << CH2_PIN) - | (1 << AUXLED_R_PIN) - | (1 << AUXLED_G_PIN) - | (1 << AUXLED_B_PIN) - ; - - // configure PWM - // Setup PWM. F_pwm = F_clkio / 2 / N / TOP, where N = prescale factor, TOP = top of counter - // pre-scale for timer: N = 1 - // WGM1[3:0]: 1,0,1,0: PWM, Phase Correct, adjustable (DS table 12-5) - // CS1[2:0]: 0,0,1: clk/1 (No prescaling) (DS table 12-6) - // COM1A[1:0]: 1,0: PWM OC1A in the normal direction (DS table 12-4) - // COM1B[1:0]: 1,0: PWM OC1B in the normal direction (DS table 12-4) - TCCR1A = (1< + +#define HWDEF_C_FILE hank/noctigon-dm11/boost/hwdef.c + +// allow using aux LEDs as extra channel modes +#include "fsm/chan-rgbaux.h" + +// channel modes: +// * 0. main LEDs +// * 1+. aux RGB +#define NUM_CHANNEL_MODES (1 + NUM_RGB_AUX_CHANNEL_MODES) +enum CHANNEL_MODES { + CM_MAIN = 0, + RGB_AUX_ENUMS +}; + +#define DEFAULT_CHANNEL_MODE CM_MAIN + +// right-most bit first, modes are in fedcba9876543210 order +#define CHANNEL_MODES_ENABLED 0b0000000000000001 +// no args +//#define USE_CHANNEL_MODE_ARGS +//#define CHANNEL_MODE_ARGS 0,0,0,0,0,0,0,0 + + +#define PWM_CHANNELS 1 // old, remove this + +#define PWM_BITS 16 // 0 to 32640 (0 to 255 PWM + 0 to 127 DSM) at constant kHz +#define PWM_GET PWM_GET16 +#define PWM_DATATYPE uint16_t +#define PWM_DATATYPE2 uint32_t // only needs 32-bit if ramp values go over 255 +#define PWM1_DATATYPE uint16_t // 15-bit PWM+DSM ramp + +#define PWM_TOP ICR1 // holds the TOP value for variable-resolution PWM +#define PWM_TOP_INIT 255 +#define PWM_CNT TCNT1 // for checking / resetting phase +// (max is (255 << 7), because it's 8-bit PWM plus 7 bits of DSM) +#define DSM_TOP (255<<7) // 15-bit resolution leaves 1 bit for carry + +// timer interrupt for DSM +#define DSM_vect TIMER1_OVF_vect +#define DSM_INTCTRL TIMSK +#define DSM_OVF_bm (1< + +#define HWDEF_C_FILE hank/noctigon-kr4/hwdef.c + +// allow using aux LEDs as extra channel modes +#include "fsm/chan-rgbaux.h" + +// channel modes: +// * 0. linear + DD FET stacked +// * 1+. aux RGB +#define NUM_CHANNEL_MODES (1 + NUM_RGB_AUX_CHANNEL_MODES) +enum CHANNEL_MODES { + CM_MAIN = 0, + RGB_AUX_ENUMS +}; + +#define DEFAULT_CHANNEL_MODE CM_MAIN + +// right-most bit first, modes are in fedcba9876543210 order +#define CHANNEL_MODES_ENABLED 0b0000000000000001 +// no args +//#define USE_CHANNEL_MODE_ARGS +//#define CHANNEL_MODE_ARGS 0,0,0,0,0,0,0,0 + + +#define PWM_CHANNELS 2 // old, remove this + +#define PWM_BITS 16 // dynamic 16-bit, but never goes over 255 +#define PWM_GET PWM_GET8 +#define PWM_DATATYPE uint16_t // is used for PWM_TOPS (which goes way over 255) +#define PWM_DATATYPE2 uint16_t // only needs 32-bit if ramp values go over 255 +#define PWM1_DATATYPE uint8_t // linear ramp +#define PWM2_DATATYPE uint8_t // DD FET ramp + +// PWM parameters of both channels are tied together because they share a counter +#define PWM_TOP ICR1 // holds the TOP value for variable-resolution PWM +#define PWM_TOP_INIT 255 // highest value used in top half of ramp +#define PWM_CNT TCNT1 // for dynamic PWM, reset phase + +// linear channel +#define CH1_PIN PB3 // pin 16, Opamp reference +#define CH1_PWM OCR1A // OCR1A is the output compare register for PB3 +#define CH1_ENABLE_PIN PB0 // pin 19, Opamp power +#define CH1_ENABLE_PORT PORTB // control port for PB0 + +// DD FET channel +#define CH2_PIN PA6 // pin 1, DD FET PWM +#define CH2_PWM OCR1B // OCR1B is the output compare register for PA6 + +// e-switch +#define SWITCH_PIN PB2 // pin 17 +#define SWITCH_PCINT PCINT10 // pin 17 pin change interrupt +#define SWITCH_PCIE PCIE1 // PCIE1 is for PCINT[11:8] +#define SWITCH_PCMSK PCMSK1 // PCMSK1 is for PCINT[11:8] +#define SWITCH_PORT PINB // PINA or PINB or PINC +#define SWITCH_PUE PUEB // pullup group B +#define PCINT_vect PCINT1_vect // ISR for PCINT[11:8] + +#define USE_VOLTAGE_DIVIDER // use a dedicated pin, not VCC, because VCC input is flattened +#define VOLTAGE_PIN PB1 // Pin 18 / PB1 / ADC6 +// pin to ADC mappings are in DS table 19-4 +#define VOLTAGE_ADC ADC6D // digital input disable pin for PB1 +// DIDR0/DIDR1 mappings are in DS section 19.13.5, 19.13.6 +#define VOLTAGE_ADC_DIDR DIDR1 // DIDR channel for ADC6D +// DS tables 19-3, 19-4 +// Bit 7 6 5 4 3 2 1 0 +// REFS1 REFS0 REFEN ADC0EN MUX3 MUX2 MUX1 MUX0 +// MUX[3:0] = 0, 1, 1, 0 for ADC6 / PB1 +// divided by ... +// REFS[1:0] = 1, 0 for internal 1.1V reference +// other bits reserved +#define ADMUX_VOLTAGE_DIVIDER 0b10000110 +#define ADC_PRSCL 0x07 // clk/128 + +// TODO: calibrate this +// Raw ADC readings at 4.4V and 2.2V +// calibrate the voltage readout here +// estimated / calculated values are: +// (voltage - D1) * (R2/(R2+R1) * 1024 / 1.1) +// D1, R1, R2 = 0, 330, 100 +#ifndef ADC_44 +//#define ADC_44 981 // raw value at 4.40V +#define ADC_44 967 // manually tweaked so 4.16V will blink out 4.2 +#endif +#ifndef ADC_22 +//#define ADC_22 489 // raw value at 2.20V +#define ADC_22 482 // manually tweaked so 4.16V will blink out 4.2 +#endif + +#define TEMP_CHANNEL 0b00001111 + +// this light has aux LEDs under the optic +#define AUXLED_R_PIN PA5 // pin 2 +#define AUXLED_G_PIN PA4 // pin 3 +#define AUXLED_B_PIN PA3 // pin 4 +#define AUXLED_RGB_PORT PORTA // PORTA or PORTB or PORTC +#define AUXLED_RGB_DDR DDRA // DDRA or DDRB or DDRC +#define AUXLED_RGB_PUE PUEA // PUEA or PUEB or PUEC + +inline void hwdef_setup() { + // enable output ports + // Opamp level and Opamp on/off + DDRB = (1 << CH1_PIN) + | (1 << CH1_ENABLE_PIN); + // DD FET PWM, aux R/G/B + DDRA = (1 << CH2_PIN) + | (1 << AUXLED_R_PIN) + | (1 << AUXLED_G_PIN) + | (1 << AUXLED_B_PIN) + ; + + // configure PWM + // Setup PWM. F_pwm = F_clkio / 2 / N / TOP, where N = prescale factor, TOP = top of counter + // pre-scale for timer: N = 1 + // WGM1[3:0]: 1,0,1,0: PWM, Phase Correct, adjustable (DS table 12-5) + // CS1[2:0]: 0,0,1: clk/1 (No prescaling) (DS table 12-6) + // COM1A[1:0]: 1,0: PWM OC1A in the normal direction (DS table 12-4) + // COM1B[1:0]: 1,0: PWM OC1B in the normal direction (DS table 12-4) + TCCR1A = (1< - -// move the switch to a different pin -#define SWITCH_PIN PB2 // pin 17 -#define SWITCH_PCINT PCINT10 // pin 17 pin change interrupt -#define SWITCH_PCIE PCIE1 // PCIE1 is for PCINT[11:8] -#define SWITCH_PCMSK PCMSK1 // PCMSK1 is for PCINT[11:8] -#define SWITCH_PORT PINB // PINA or PINB or PINC -#define SWITCH_PUE PUEB // pullup group B -#define PCINT_vect PCINT1_vect // ISR for PCINT[11:8] - -// the rest of the config is the same as the generic Emisar 2ch build -#include "hank/emisar-2ch/hwdef.h" - diff --git a/hw/hank/noctigon-kr4-boost/anduril.h b/hw/hank/noctigon-kr4-boost/anduril.h deleted file mode 100644 index f0c5b92..0000000 --- a/hw/hank/noctigon-kr4-boost/anduril.h +++ /dev/null @@ -1,16 +0,0 @@ -// Noctigon KR4 (12V) config options for Anduril -// (and Noctigon KR1) -// Copyright (C) 2020-2023 Selene ToyKeeper -// SPDX-License-Identifier: GPL-3.0-or-later -#pragma once - -// the only things different from dm11-boost are: -// - e-switch is on a different pin (defined in hwdef) -// - different model number -#include "hank/noctigon-dm11-boost/anduril.h" -#include "hank/noctigon-kr4-boost/hwdef.h" -#undef MODEL_NUMBER -#define MODEL_NUMBER "0216" -#include "hank/anduril.h" -// ATTINY: 1634 - diff --git a/hw/hank/noctigon-kr4-boost/hwdef.h b/hw/hank/noctigon-kr4-boost/hwdef.h deleted file mode 100644 index 1ee2627..0000000 --- a/hw/hank/noctigon-kr4-boost/hwdef.h +++ /dev/null @@ -1,57 +0,0 @@ -// Noctigon KR4 boost driver layout (attiny1634) -// Copyright (C) 2020-2023 Selene ToyKeeper -// SPDX-License-Identifier: GPL-3.0-or-later -#pragma once - -/* - * (based on Noctigon DM11-boost and KR4) - * (is basically the same except the switch is on a different pin) - * - * Pin / Name / Function - * 1 PA6 (none) (PWM1B) (reserved for DD drivers) - * 2 PA5 R: red aux LED (PWM0B) - * 3 PA4 G: green aux LED - * 4 PA3 B: blue aux LED - * 5 PA2 L: button LED - * 6 PA1 (none) - * 7 PA0 (none) - * 8 GND GND - * 9 VCC VCC - * 10 PC5 (none) - * 11 PC4 (none) - * 12 PC3 RESET - * 13 PC2 (none) - * 14 PC1 SCK - * 15 PC0 boost PMIC enable (PWM0A not used) - * 16 PB3 main LED PWM (PWM1A) - * 17 PB2 MISO / e-switch (PCINT10) - * 18 PB1 MOSI / battery voltage (ADC6) - * 19 PB0 Opamp power - * 20 PA7 (none) (PCINT7) - * ADC12 thermal sensor - * - * Main LED power uses one pin to turn the Opamp on/off, - * and one pin to control Opamp power level. - * Linear brightness control uses the power level pin, with dynamic PWM. - * The on/off pin is only used to turn the main LED on and off, - * not to change brightness. - */ - -#include "hank/noctigon-dm11-boost/hwdef.h" - -// e-switch is on a different pin -#undef SWITCH_PIN -#undef SWITCH_PCINT -#undef SWITCH_PCIE -#undef SWITCH_PCMSK -#undef SWITCH_PORT -#undef SWITCH_PUE -#undef PCINT_vect -#define SWITCH_PIN PB2 // pin 17 -#define SWITCH_PCINT PCINT10 // pin 17 pin change interrupt -#define SWITCH_PCIE PCIE1 // PCIE1 is for PCINT[11:8] -#define SWITCH_PCMSK PCMSK1 // PCMSK1 is for PCINT[11:8] -#define SWITCH_PORT PINB // PINA or PINB or PINC -#define SWITCH_PUE PUEB // pullup group B -#define PCINT_vect PCINT1_vect // ISR for PCINT[11:8] - diff --git a/hw/hank/noctigon-kr4-nofet/anduril.h b/hw/hank/noctigon-kr4-nofet/anduril.h deleted file mode 100644 index 0198e33..0000000 --- a/hw/hank/noctigon-kr4-nofet/anduril.h +++ /dev/null @@ -1,66 +0,0 @@ -// Noctigon KR4 (no DD FET) config options for Anduril -// Copyright (C) 2020-2023 Selene ToyKeeper -// SPDX-License-Identifier: GPL-3.0-or-later -#pragma once - -// (and Noctigon KR1) -// (and Emisar D4v2 E21A, a.k.a. "D4v2.5") -#define HWDEF_C_FILE hank/noctigon-kr4-nofet/hwdef.c -#include "hank/noctigon-kr4/anduril.h" -#undef MODEL_NUMBER -#define MODEL_NUMBER "0212" -// ATTINY: 1634 - -// brightness w/ SST-20 4000K LEDs: -// 0/1023: 0.35 lm -// 1/1023: 2.56 lm -// max regulated: 1740 lm -#undef PWM_CHANNELS -#define PWM_CHANNELS 1 -#define RAMP_SIZE 150 -// prioritize low lows, at risk of visible ripple -// level_calc.py 5.01 1 149 7135 1 0.3 1740 --pwm dyn:78:16384:255 -#undef PWM1_LEVELS -#define PWM1_LEVELS 0,1,1,1,2,3,3,4,5,6,7,8,9,10,11,13,14,16,17,19,21,23,25,27,29,31,34,36,39,42,44,47,50,53,57,60,63,67,70,74,77,81,85,88,92,96,99,103,107,110,113,117,120,123,126,128,130,133,134,136,137,137,137,137,136,135,133,130,126,122,117,111,104,96,87,76,65,52,38,22,23,25,26,27,28,29,30,32,33,34,36,37,39,40,42,43,45,47,49,51,53,55,57,59,61,63,66,68,70,73,76,78,81,84,87,90,93,96,99,103,106,110,113,117,121,125,129,133,137,142,146,151,155,160,165,170,175,181,186,192,197,203,209,215,222,228,234,241,248,255 -#undef PWM2_LEVELS -#undef PWM_TOPS -#define PWM_TOPS 16383,16383,12404,8140,11462,14700,11041,12947,13795,14111,14124,13946,13641,13248,12791,13418,12808,13057,12385,12428,12358,12209,12000,11746,11459,11147,11158,10793,10708,10576,10173,9998,9800,9585,9527,9278,9023,8901,8634,8486,8216,8053,7881,7615,7440,7261,7009,6832,6656,6422,6196,6031,5819,5615,5419,5190,4973,4803,4571,4386,4179,3955,3745,3549,3340,3145,2940,2729,2513,2312,2109,1903,1697,1491,1286,1070,871,662,459,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 -#undef DEFAULT_LEVEL -#define DEFAULT_LEVEL 50 -#undef MAX_1x7135 -#define MAX_1x7135 150 - -#undef RAMP_SMOOTH_FLOOR -#undef RAMP_SMOOTH_CEIL -#undef RAMP_DISCRETE_FLOOR -#undef RAMP_DISCRETE_CEIL -#undef RAMP_DISCRETE_STEPS - -#define RAMP_SMOOTH_FLOOR 11 // low levels may be unreliable -#define RAMP_SMOOTH_CEIL 130 -// 11, 30, [50], 70, 90, 110, 130 (plus [150] on turbo) -#define RAMP_DISCRETE_FLOOR 11 -#define RAMP_DISCRETE_CEIL RAMP_SMOOTH_CEIL -#define RAMP_DISCRETE_STEPS 7 - -// safe limit ~1000 lm (can sustain 900 lm) -#undef SIMPLE_UI_FLOOR -#undef SIMPLE_UI_CEIL -#define SIMPLE_UI_FLOOR RAMP_DISCRETE_FLOOR -#define SIMPLE_UI_CEIL RAMP_DISCRETE_CEIL - - -// slow down party strobe; this driver can't pulse for 1ms or less -// (only needed on no-FET build) -#define PARTY_STROBE_ONTIME 2 - -// jump start a bit higher than base driver -#undef DEFAULT_JUMP_START_LEVEL -#define DEFAULT_JUMP_START_LEVEL 25 - -// stop panicking at ~1300 lm -#undef THERM_FASTER_LEVEL -#define THERM_FASTER_LEVEL 140 -#undef MIN_THERM_STEPDOWN -#define MIN_THERM_STEPDOWN 80 // must be > end of dynamic PWM range - diff --git a/hw/hank/noctigon-kr4-nofet/hwdef.c b/hw/hank/noctigon-kr4-nofet/hwdef.c deleted file mode 100644 index 783eeed..0000000 --- a/hw/hank/noctigon-kr4-nofet/hwdef.c +++ /dev/null @@ -1,60 +0,0 @@ -// Noctigon KR4 (no DD FET) PWM helper functions -// Copyright (C) 2020-2023 Selene ToyKeeper -// SPDX-License-Identifier: GPL-3.0-or-later - -#pragma once - -#include "fsm/chan-rgbaux.c" - -void set_level_zero(); - -void set_level_main(uint8_t level); -bool gradual_tick_main(uint8_t gt); - - -Channel channels[] = { - { // channel 1 only - .set_level = set_level_main, - .gradual_tick = gradual_tick_main - }, - RGB_AUX_CHANNELS -}; - - -void set_level_zero() { - CH1_PWM = 0; - CH2_PWM = 0; - PWM_CNT = 0; // reset phase - CH1_ENABLE_PORT &= ~(1 << CH1_ENABLE_PIN); // disable opamp -} - -// single set of LEDs with linear power channel -void set_level_main(uint8_t level) { - CH1_ENABLE_PORT |= (1 << CH1_ENABLE_PIN); // enable opamp - - PWM_DATATYPE ch1_pwm = PWM_GET(pwm1_levels, level); - // pulse frequency modulation, a.k.a. dynamic PWM - uint16_t top = PWM_GET16(pwm_tops, level); - - CH1_PWM = ch1_pwm; - CH2_PWM = 0; - // wait to sync the counter and avoid flashes - while(actual_level && (PWM_CNT > (top - 32))) {} - PWM_TOP = top; - // force reset phase when turning on from zero - // (because otherwise the initial response is inconsistent) - if (! actual_level) PWM_CNT = 0; -} - -bool gradual_tick_main(uint8_t gt) { - PWM_DATATYPE pwm1 = PWM_GET(pwm1_levels, gt); - - GRADUAL_ADJUST_SIMPLE(pwm1, CH1_PWM); - - if ( (pwm1 == CH1_PWM) - ) { - return true; // done - } - return false; // not done yet -} - diff --git a/hw/hank/noctigon-kr4/219/anduril.h b/hw/hank/noctigon-kr4/219/anduril.h new file mode 100644 index 0000000..cd3e118 --- /dev/null +++ b/hw/hank/noctigon-kr4/219/anduril.h @@ -0,0 +1,17 @@ +// Noctigon KR4 (reduced FET) config options for Anduril +// Copyright (C) 2020-2023 Selene ToyKeeper +// SPDX-License-Identifier: GPL-3.0-or-later +#pragma once + +#include "hank/noctigon-kr4/anduril.h" +#undef MODEL_NUMBER +#define MODEL_NUMBER "0213" +// ATTINY: 1634 + +// don't turn off first channel at turbo level +#undef PWM1_LEVELS +#define PWM1_LEVELS 0,1,1,2,2,3,4,5,6,7,8,9,11,12,14,16,17,19,22,24,26,29,31,34,37,40,43,46,49,53,56,60,63,67,71,74,78,82,86,89,93,96,99,103,105,108,110,112,114,115,116,116,115,114,112,109,106,101,95,89,81,71,60,48,34,19,20,21,22,23,24,26,27,28,30,31,32,34,36,37,39,41,43,45,47,49,51,53,56,58,61,63,66,69,72,75,78,81,84,88,91,95,99,103,107,111,115,119,124,129,133,138,143,149,154,159,165,171,177,183,189,196,203,210,217,224,231,239,247,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 +// 60% FET power +#undef PWM2_LEVELS +#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,6,12,18,25,32,38,45,53,60,68,75,83,91,99,108,117,125,135,144,153 + diff --git a/hw/hank/noctigon-kr4/219b/anduril.h b/hw/hank/noctigon-kr4/219b/anduril.h new file mode 100644 index 0000000..9c113f9 --- /dev/null +++ b/hw/hank/noctigon-kr4/219b/anduril.h @@ -0,0 +1,17 @@ +// Noctigon KR4 (reduced FET) config options for Anduril +// Copyright (C) 2020-2023 Selene ToyKeeper +// SPDX-License-Identifier: GPL-3.0-or-later +#pragma once + +#include "hank/noctigon-kr4/anduril.h" +#undef MODEL_NUMBER +#define MODEL_NUMBER "0214" +// ATTINY: 1634 + +// don't turn off first channel at turbo level +#undef PWM1_LEVELS +#define PWM1_LEVELS 0,1,1,2,2,3,4,5,6,7,8,9,11,12,14,16,17,19,22,24,26,29,31,34,37,40,43,46,49,53,56,60,63,67,71,74,78,82,86,89,93,96,99,103,105,108,110,112,114,115,116,116,115,114,112,109,106,101,95,89,81,71,60,48,34,19,20,21,22,23,24,26,27,28,30,31,32,34,36,37,39,41,43,45,47,49,51,53,56,58,61,63,66,69,72,75,78,81,84,88,91,95,99,103,107,111,115,119,124,129,133,138,143,149,154,159,165,171,177,183,189,196,203,210,217,224,231,239,247,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 +// 50% FET power +#undef PWM2_LEVELS +#define PWM2_LEVELS 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,5,10,15,21,26,32,38,44,50,56,63,69,76,83,90,97,104,112,120,128 + diff --git a/hw/hank/noctigon-kr4/2ch/anduril.h b/hw/hank/noctigon-kr4/2ch/anduril.h new file mode 100644 index 0000000..be7c4d0 --- /dev/null +++ b/hw/hank/noctigon-kr4/2ch/anduril.h @@ -0,0 +1,16 @@ +// Noctigon KR4 2-channel config options for Anduril +// Copyright (C) 2021-2023 Selene ToyKeeper +// SPDX-License-Identifier: GPL-3.0-or-later +#pragma once + +// (basically the same as Emisar generic 2-channel build, +// but switch on a different pin, and no lighted button) +// ATTINY: 1634 +#include "hank/noctigon-kr4/2ch/hwdef.h" +#include "hank/emisar-2ch/anduril.h" +#undef MODEL_NUMBER +#define MODEL_NUMBER "0215" + +// the button doesn't light up +#undef USE_BUTTON_LED + diff --git a/hw/hank/noctigon-kr4/2ch/hwdef.h b/hw/hank/noctigon-kr4/2ch/hwdef.h new file mode 100644 index 0000000..081fccc --- /dev/null +++ b/hw/hank/noctigon-kr4/2ch/hwdef.h @@ -0,0 +1,47 @@ +// Noctigon KR4 w/ tint ramping +// Copyright (C) 2021-2023 Selene ToyKeeper +// SPDX-License-Identifier: GPL-3.0-or-later +#pragma once + +/* + * (same driver as emisar-2ch, but with the switch on a different pin) + * + * Pin / Name / Function + * 1 PA6 2nd LED PWM (linear) (PWM1B) + * 2 PA5 R: red aux LED (PWM0B) + * 3 PA4 G: green aux LED + * 4 PA3 B: blue aux LED + * 5 PA2 button LED + * 6 PA1 Opamp 2 enable (2nd LEDs) + * 7 PA0 Opamp 1 enable (main LEDs) + * 8 GND GND + * 9 VCC VCC + * 10 PC5 (none) + * 11 PC4 (none) + * 12 PC3 RESET + * 13 PC2 (none) + * 14 PC1 SCK + * 15 PC0 main LED PWM (FET) (PWM0A) (unused on some models because tint ramping) + * 16 PB3 main LED PWM (linear) (PWM1A) + * 17 PB2 MISO / e-switch (PCINT10) + * 18 PB1 MOSI / battery voltage (ADC6) + * 19 PB0 (none) + * 20 PA7 (none) + * ADC12 thermal sensor + */ + +#define ATTINY 1634 +#include + +// move the switch to a different pin +#define SWITCH_PIN PB2 // pin 17 +#define SWITCH_PCINT PCINT10 // pin 17 pin change interrupt +#define SWITCH_PCIE PCIE1 // PCIE1 is for PCINT[11:8] +#define SWITCH_PCMSK PCMSK1 // PCMSK1 is for PCINT[11:8] +#define SWITCH_PORT PINB // PINA or PINB or PINC +#define SWITCH_PUE PUEB // pullup group B +#define PCINT_vect PCINT1_vect // ISR for PCINT[11:8] + +// the rest of the config is the same as the generic Emisar 2ch build +#include "hank/emisar-2ch/hwdef.h" + diff --git a/hw/hank/noctigon-kr4/boost/anduril.h b/hw/hank/noctigon-kr4/boost/anduril.h new file mode 100644 index 0000000..a3b33ee --- /dev/null +++ b/hw/hank/noctigon-kr4/boost/anduril.h @@ -0,0 +1,16 @@ +// Noctigon KR4 (12V) config options for Anduril +// (and Noctigon KR1) +// Copyright (C) 2020-2023 Selene ToyKeeper +// SPDX-License-Identifier: GPL-3.0-or-later +#pragma once + +// the only things different from dm11-boost are: +// - e-switch is on a different pin (defined in hwdef) +// - different model number +#include "hank/noctigon-dm11/boost/anduril.h" +#include "hank/noctigon-kr4/boost/hwdef.h" +#undef MODEL_NUMBER +#define MODEL_NUMBER "0216" +#include "hank/anduril.h" +// ATTINY: 1634 + diff --git a/hw/hank/noctigon-kr4/boost/hwdef.h b/hw/hank/noctigon-kr4/boost/hwdef.h new file mode 100644 index 0000000..f17d263 --- /dev/null +++ b/hw/hank/noctigon-kr4/boost/hwdef.h @@ -0,0 +1,57 @@ +// Noctigon KR4 boost driver layout (attiny1634) +// Copyright (C) 2020-2023 Selene ToyKeeper +// SPDX-License-Identifier: GPL-3.0-or-later +#pragma once + +/* + * (based on Noctigon DM11-boost and KR4) + * (is basically the same except the switch is on a different pin) + * + * Pin / Name / Function + * 1 PA6 (none) (PWM1B) (reserved for DD drivers) + * 2 PA5 R: red aux LED (PWM0B) + * 3 PA4 G: green aux LED + * 4 PA3 B: blue aux LED + * 5 PA2 L: button LED + * 6 PA1 (none) + * 7 PA0 (none) + * 8 GND GND + * 9 VCC VCC + * 10 PC5 (none) + * 11 PC4 (none) + * 12 PC3 RESET + * 13 PC2 (none) + * 14 PC1 SCK + * 15 PC0 boost PMIC enable (PWM0A not used) + * 16 PB3 main LED PWM (PWM1A) + * 17 PB2 MISO / e-switch (PCINT10) + * 18 PB1 MOSI / battery voltage (ADC6) + * 19 PB0 Opamp power + * 20 PA7 (none) (PCINT7) + * ADC12 thermal sensor + * + * Main LED power uses one pin to turn the Opamp on/off, + * and one pin to control Opamp power level. + * Linear brightness control uses the power level pin, with dynamic PWM. + * The on/off pin is only used to turn the main LED on and off, + * not to change brightness. + */ + +#include "hank/noctigon-dm11/boost/hwdef.h" + +// e-switch is on a different pin +#undef SWITCH_PIN +#undef SWITCH_PCINT +#undef SWITCH_PCIE +#undef SWITCH_PCMSK +#undef SWITCH_PORT +#undef SWITCH_PUE +#undef PCINT_vect +#define SWITCH_PIN PB2 // pin 17 +#define SWITCH_PCINT PCINT10 // pin 17 pin change interrupt +#define SWITCH_PCIE PCIE1 // PCIE1 is for PCINT[11:8] +#define SWITCH_PCMSK PCMSK1 // PCMSK1 is for PCINT[11:8] +#define SWITCH_PORT PINB // PINA or PINB or PINC +#define SWITCH_PUE PUEB // pullup group B +#define PCINT_vect PCINT1_vect // ISR for PCINT[11:8] + diff --git a/hw/hank/noctigon-kr4/nofet/anduril.h b/hw/hank/noctigon-kr4/nofet/anduril.h new file mode 100644 index 0000000..10c0bf8 --- /dev/null +++ b/hw/hank/noctigon-kr4/nofet/anduril.h @@ -0,0 +1,66 @@ +// Noctigon KR4 (no DD FET) config options for Anduril +// Copyright (C) 2020-2023 Selene ToyKeeper +// SPDX-License-Identifier: GPL-3.0-or-later +#pragma once + +// (and Noctigon KR1) +// (and Emisar D4v2 E21A, a.k.a. "D4v2.5") +#define HWDEF_C_FILE hank/noctigon-kr4/nofet/hwdef.c +#include "hank/noctigon-kr4/anduril.h" +#undef MODEL_NUMBER +#define MODEL_NUMBER "0212" +// ATTINY: 1634 + +// brightness w/ SST-20 4000K LEDs: +// 0/1023: 0.35 lm +// 1/1023: 2.56 lm +// max regulated: 1740 lm +#undef PWM_CHANNELS +#define PWM_CHANNELS 1 +#define RAMP_SIZE 150 +// prioritize low lows, at risk of visible ripple +// level_calc.py 5.01 1 149 7135 1 0.3 1740 --pwm dyn:78:16384:255 +#undef PWM1_LEVELS +#define PWM1_LEVELS 0,1,1,1,2,3,3,4,5,6,7,8,9,10,11,13,14,16,17,19,21,23,25,27,29,31,34,36,39,42,44,47,50,53,57,60,63,67,70,74,77,81,85,88,92,96,99,103,107,110,113,117,120,123,126,128,130,133,134,136,137,137,137,137,136,135,133,130,126,122,117,111,104,96,87,76,65,52,38,22,23,25,26,27,28,29,30,32,33,34,36,37,39,40,42,43,45,47,49,51,53,55,57,59,61,63,66,68,70,73,76,78,81,84,87,90,93,96,99,103,106,110,113,117,121,125,129,133,137,142,146,151,155,160,165,170,175,181,186,192,197,203,209,215,222,228,234,241,248,255 +#undef PWM2_LEVELS +#undef PWM_TOPS +#define PWM_TOPS 16383,16383,12404,8140,11462,14700,11041,12947,13795,14111,14124,13946,13641,13248,12791,13418,12808,13057,12385,12428,12358,12209,12000,11746,11459,11147,11158,10793,10708,10576,10173,9998,9800,9585,9527,9278,9023,8901,8634,8486,8216,8053,7881,7615,7440,7261,7009,6832,6656,6422,6196,6031,5819,5615,5419,5190,4973,4803,4571,4386,4179,3955,3745,3549,3340,3145,2940,2729,2513,2312,2109,1903,1697,1491,1286,1070,871,662,459,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255 +#undef DEFAULT_LEVEL +#define DEFAULT_LEVEL 50 +#undef MAX_1x7135 +#define MAX_1x7135 150 + +#undef RAMP_SMOOTH_FLOOR +#undef RAMP_SMOOTH_CEIL +#undef RAMP_DISCRETE_FLOOR +#undef RAMP_DISCRETE_CEIL +#undef RAMP_DISCRETE_STEPS + +#define RAMP_SMOOTH_FLOOR 11 // low levels may be unreliable +#define RAMP_SMOOTH_CEIL 130 +// 11, 30, [50], 70, 90, 110, 130 (plus [150] on turbo) +#define RAMP_DISCRETE_FLOOR 11 +#define RAMP_DISCRETE_CEIL RAMP_SMOOTH_CEIL +#define RAMP_DISCRETE_STEPS 7 + +// safe limit ~1000 lm (can sustain 900 lm) +#undef SIMPLE_UI_FLOOR +#undef SIMPLE_UI_CEIL +#define SIMPLE_UI_FLOOR RAMP_DISCRETE_FLOOR +#define SIMPLE_UI_CEIL RAMP_DISCRETE_CEIL + + +// slow down party strobe; this driver can't pulse for 1ms or less +// (only needed on no-FET build) +#define PARTY_STROBE_ONTIME 2 + +// jump start a bit higher than base driver +#undef DEFAULT_JUMP_START_LEVEL +#define DEFAULT_JUMP_START_LEVEL 25 + +// stop panicking at ~1300 lm +#undef THERM_FASTER_LEVEL +#define THERM_FASTER_LEVEL 140 +#undef MIN_THERM_STEPDOWN +#define MIN_THERM_STEPDOWN 80 // must be > end of dynamic PWM range + diff --git a/hw/hank/noctigon-kr4/nofet/hwdef.c b/hw/hank/noctigon-kr4/nofet/hwdef.c new file mode 100644 index 0000000..783eeed --- /dev/null +++ b/hw/hank/noctigon-kr4/nofet/hwdef.c @@ -0,0 +1,60 @@ +// Noctigon KR4 (no DD FET) PWM helper functions +// Copyright (C) 2020-2023 Selene ToyKeeper +// SPDX-License-Identifier: GPL-3.0-or-later + +#pragma once + +#include "fsm/chan-rgbaux.c" + +void set_level_zero(); + +void set_level_main(uint8_t level); +bool gradual_tick_main(uint8_t gt); + + +Channel channels[] = { + { // channel 1 only + .set_level = set_level_main, + .gradual_tick = gradual_tick_main + }, + RGB_AUX_CHANNELS +}; + + +void set_level_zero() { + CH1_PWM = 0; + CH2_PWM = 0; + PWM_CNT = 0; // reset phase + CH1_ENABLE_PORT &= ~(1 << CH1_ENABLE_PIN); // disable opamp +} + +// single set of LEDs with linear power channel +void set_level_main(uint8_t level) { + CH1_ENABLE_PORT |= (1 << CH1_ENABLE_PIN); // enable opamp + + PWM_DATATYPE ch1_pwm = PWM_GET(pwm1_levels, level); + // pulse frequency modulation, a.k.a. dynamic PWM + uint16_t top = PWM_GET16(pwm_tops, level); + + CH1_PWM = ch1_pwm; + CH2_PWM = 0; + // wait to sync the counter and avoid flashes + while(actual_level && (PWM_CNT > (top - 32))) {} + PWM_TOP = top; + // force reset phase when turning on from zero + // (because otherwise the initial response is inconsistent) + if (! actual_level) PWM_CNT = 0; +} + +bool gradual_tick_main(uint8_t gt) { + PWM_DATATYPE pwm1 = PWM_GET(pwm1_levels, gt); + + GRADUAL_ADJUST_SIMPLE(pwm1, CH1_PWM); + + if ( (pwm1 == CH1_PWM) + ) { + return true; // done + } + return false; // not done yet +} + -- cgit v1.2.3