trennfix/sw: Nice, keep! Good!
authorPhilipp Hachtmann <hachti@hachti.de>
Sun, 12 Feb 2017 15:58:09 +0000 (16:58 +0100)
committerPhilipp Hachtmann <hachti@hachti.de>
Sun, 12 Feb 2017 17:04:25 +0000 (18:04 +0100)
Signed-off-by: Philipp Hachtmann <hachti@hachti.de>
14 files changed:
trennfix/pcb/trennfix.brd
trennfix/pcb/trennfix.sch
trennfix/sw/Makefile
trennfix/sw/config/hardware.h
trennfix/sw/config/trennfix_0.4.h [new file with mode: 0644]
trennfix/sw/config/trennfix_attiny25.h [deleted file]
trennfix/sw/config/trennfix_attiny85.h [deleted file]
trennfix/sw/include/pin_magic.h [new file with mode: 0644]
trennfix/sw/mk/trennfix_0.4.mk [new file with mode: 0644]
trennfix/sw/mk/trennfix_attiny25.mk [deleted file]
trennfix/sw/mk/trennfix_attiny85.mk [deleted file]
trennfix/sw/mm/src/mm_switch.c
trennfix/sw/pin_magic.h [deleted file]
trennfix/sw/src/main.c

index c09b8776e7edadbf1ff305b50c2f07976787bab8..4591f0a3e3191009361065cf3410aebc1937a4f9 100644 (file)
@@ -2914,13 +2914,13 @@ Your Multi-CB Team
 <attribute name="NAME" x="12.7" y="14.12875" size="0.8128" layer="25" font="vector" ratio="10" rot="R90"/>
 <attribute name="VALUE" x="16.66875" y="9.68375" size="1.27" layer="27" rot="R90"/>
 </element>
-<element name="LD1" library="led" package="CHIP-LED0805" value="" x="14.2875" y="26.82875" smashed="yes">
-<attribute name="NAME" x="12.85875" y="27.78125" size="0.8128" layer="25" font="vector" rot="R270"/>
-<attribute name="VALUE" x="16.8275" y="25.55875" size="1.27" layer="27" rot="R90"/>
+<element name="LD1" library="led" package="CHIP-LED0805" value="" x="14.2875" y="25.7175" smashed="yes">
+<attribute name="NAME" x="12.85875" y="26.67" size="0.8128" layer="25" font="vector" rot="R270"/>
+<attribute name="VALUE" x="16.8275" y="24.4475" size="1.27" layer="27" rot="R90"/>
 </element>
-<element name="R6" library="rcl" package="R0805" value="470" x="14.224" y="23.24735" smashed="yes" rot="R270">
-<attribute name="NAME" x="15.65275" y="22.7711" size="0.8128" layer="25" font="vector" rot="R270"/>
-<attribute name="VALUE" x="11.684" y="23.88235" size="1.27" layer="27" rot="R270"/>
+<element name="R6" library="rcl" package="R0805" value="470" x="14.224" y="20.2311" smashed="yes" rot="R270">
+<attribute name="NAME" x="15.65275" y="19.75485" size="0.8128" layer="25" font="vector" rot="R270"/>
+<attribute name="VALUE" x="11.684" y="20.8661" size="1.27" layer="27" rot="R270"/>
 </element>
 <element name="S-1" library="testpad" package="TP20SQ" value="TPTP20SQ" x="14.24305" y="30.96895">
 <attribute name="TP_SIGNAL_NAME" value="" x="7.94385" y="38.38575" size="1.778" layer="27" display="off"/>
@@ -2936,12 +2936,6 @@ Your Multi-CB Team
 <attribute name="TP_SIGNAL_NAME" value="" x="10.95375" y="30.95625" size="1.778" layer="27" display="off"/>
 </element>
 <element name="D4" library="diode" package="SOD123FL" value="5V" x="1.42875" y="2.69875" rot="R270"/>
-<element name="L" library="testpad" package="TP20SQ" value="TPTP20SQ" x="14.2875" y="20.0025">
-<attribute name="TP_SIGNAL_NAME" value="" x="14.2875" y="20.0025" size="1.778" layer="27" display="off"/>
-</element>
-<element name="G" library="testpad" package="TP20SQ" value="TPTP20SQ" x="10.00125" y="18.7325">
-<attribute name="TP_SIGNAL_NAME" value="" x="10.00125" y="18.7325" size="1.778" layer="27" display="off"/>
-</element>
 </elements>
 <signals>
 <signal name="GND">
@@ -2973,7 +2967,7 @@ Your Multi-CB Team
 <contactref element="LD1" pad="C"/>
 <contactref element="T1" pad="2"/>
 <contactref element="R5" pad="2"/>
-<via x="14.76375" y="29.05125" extent="1-16" drill="0.2"/>
+<via x="14.44625" y="28.41625" extent="1-16" drill="0.2"/>
 <via x="7.9375" y="25.24125" extent="1-16" drill="0.2"/>
 <via x="3.33375" y="26.3525" extent="1-16" drill="0.2"/>
 <via x="3.33375" y="24.28875" extent="1-16" drill="0.2"/>
@@ -2981,8 +2975,8 @@ Your Multi-CB Team
 <via x="7.46125" y="16.1925" extent="1-16" drill="0.2"/>
 <via x="2.06375" y="20.16125" extent="1-16" drill="0.2"/>
 <via x="2.06375" y="18.0975" extent="1-16" drill="0.2"/>
-<via x="9.525" y="20.6375" extent="1-16" drill="0.2"/>
-<via x="9.04875" y="16.1925" extent="1-16" drill="0.2"/>
+<via x="10.95375" y="18.25625" extent="1-16" drill="0.2"/>
+<via x="9.8425" y="19.52625" extent="1-16" drill="0.2"/>
 <via x="14.2875" y="3.01625" extent="1-16" drill="0.2"/>
 <via x="13.97" y="4.28625" extent="1-16" drill="0.2"/>
 <via x="11.90625" y="4.92125" extent="1-16" drill="0.2"/>
@@ -2994,7 +2988,6 @@ Your Multi-CB Team
 <via x="5.3975" y="2.06375" extent="1-16" drill="0.2"/>
 <via x="8.255" y="30.00375" extent="1-16" drill="0.2"/>
 <contactref element="D4" pad="A"/>
-<contactref element="G" pad="TP"/>
 </signal>
 <signal name="0">
 <contactref element="D1" pad="AC1"/>
@@ -3187,17 +3180,13 @@ Your Multi-CB Team
 <wire x1="14.9225" y1="14.9225" x2="14.9225" y2="17.62125" width="0.1524" layer="16"/>
 <via x="14.9225" y="17.62125" extent="1-16" drill="0.2"/>
 <wire x1="14.9225" y1="17.62125" x2="14.224" y2="18.31975" width="0.1524" layer="1"/>
-<wire x1="14.224" y1="18.31975" x2="14.224" y2="20.47875" width="0.1524" layer="1"/>
-<contactref element="L" pad="TP"/>
-<wire x1="14.224" y1="20.47875" x2="14.224" y2="22.29735" width="0.1524" layer="1"/>
-<wire x1="14.2875" y1="20.0025" x2="14.224" y2="20.32" width="0.4064" layer="1"/>
-<wire x1="14.224" y1="20.32" x2="14.224" y2="20.47875" width="0.4064" layer="1"/>
+<wire x1="14.224" y1="18.31975" x2="14.224" y2="19.2811" width="0.1524" layer="1"/>
 </signal>
 <signal name="N$2">
 <contactref element="R6" pad="1"/>
 <contactref element="LD1" pad="A"/>
-<wire x1="14.2875" y1="25.77875" x2="14.2875" y2="24.4196" width="0.1524" layer="1"/>
-<wire x1="14.2875" y1="24.4196" x2="14.224" y2="24.19735" width="0.1524" layer="1"/>
+<wire x1="14.2875" y1="24.6675" x2="14.2875" y2="21.2446" width="0.1524" layer="1"/>
+<wire x1="14.2875" y1="21.2446" x2="14.224" y2="21.1811" width="0.1524" layer="1"/>
 </signal>
 <signal name="OUT1">
 <contactref element="S-1" pad="TP"/>
index bee2cb74f6b44d6f6973d44a96a673ad61dff24f..4089d34143d4c84225060103f0bddf0a98f43fa8 100644 (file)
@@ -8,34 +8,34 @@
 </settings>
 <grid distance="25" unitdist="mil" unit="mil" style="lines" multiple="1" display="yes" altdistance="0.01" altunitdist="inch" altunit="inch"/>
 <layers>
-<layer number="1" name="Top" color="4" fill="1" visible="no" active="no"/>
-<layer number="2" name="Route2" color="1" fill="3" visible="no" active="no"/>
-<layer number="3" name="Route3" color="4" fill="3" visible="no" active="no"/>
-<layer number="4" name="Route4" color="1" fill="4" visible="no" active="no"/>
-<layer number="5" name="Route5" color="4" fill="4" visible="no" active="no"/>
-<layer number="6" name="Route6" color="1" fill="8" visible="no" active="no"/>
-<layer number="7" name="Route7" color="4" fill="8" visible="no" active="no"/>
-<layer number="8" name="Route8" color="1" fill="2" visible="no" active="no"/>
-<layer number="9" name="Route9" color="4" fill="2" visible="no" active="no"/>
-<layer number="10" name="Route10" color="1" fill="7" visible="no" active="no"/>
-<layer number="11" name="Route11" color="4" fill="7" visible="no" active="no"/>
-<layer number="12" name="Route12" color="1" fill="5" visible="no" active="no"/>
-<layer number="13" name="Route13" color="4" fill="5" visible="no" active="no"/>
-<layer number="14" name="Route14" color="1" fill="6" visible="no" active="no"/>
-<layer number="15" name="Route15" color="4" fill="6" visible="no" active="no"/>
-<layer number="16" name="Bottom" color="1" fill="1" visible="no" active="no"/>
-<layer number="17" name="Pads" color="2" fill="1" visible="no" active="no"/>
-<layer number="18" name="Vias" color="2" fill="1" visible="no" active="no"/>
-<layer number="19" name="Unrouted" color="6" fill="1" visible="no" active="no"/>
-<layer number="20" name="Dimension" color="15" fill="1" visible="no" active="no"/>
-<layer number="21" name="tPlace" color="7" fill="1" visible="no" active="no"/>
-<layer number="22" name="bPlace" color="7" fill="1" visible="no" active="no"/>
-<layer number="23" name="tOrigins" color="15" fill="1" visible="no" active="no"/>
-<layer number="24" name="bOrigins" color="15" fill="1" visible="no" active="no"/>
-<layer number="25" name="tNames" color="7" fill="1" visible="no" active="no"/>
-<layer number="26" name="bNames" color="7" fill="1" visible="no" active="no"/>
-<layer number="27" name="tValues" color="7" fill="1" visible="no" active="no"/>
-<layer number="28" name="bValues" color="7" fill="1" visible="no" active="no"/>
+<layer number="1" name="Top" color="4" fill="1" visible="yes" active="no"/>
+<layer number="2" name="Route2" color="1" fill="3" visible="yes" active="no"/>
+<layer number="3" name="Route3" color="4" fill="3" visible="yes" active="no"/>
+<layer number="4" name="Route4" color="1" fill="4" visible="yes" active="no"/>
+<layer number="5" name="Route5" color="4" fill="4" visible="yes" active="no"/>
+<layer number="6" name="Route6" color="1" fill="8" visible="yes" active="no"/>
+<layer number="7" name="Route7" color="4" fill="8" visible="yes" active="no"/>
+<layer number="8" name="Route8" color="1" fill="2" visible="yes" active="no"/>
+<layer number="9" name="Route9" color="4" fill="2" visible="yes" active="no"/>
+<layer number="10" name="Route10" color="1" fill="7" visible="yes" active="no"/>
+<layer number="11" name="Route11" color="4" fill="7" visible="yes" active="no"/>
+<layer number="12" name="Route12" color="1" fill="5" visible="yes" active="no"/>
+<layer number="13" name="Route13" color="4" fill="5" visible="yes" active="no"/>
+<layer number="14" name="Route14" color="1" fill="6" visible="yes" active="no"/>
+<layer number="15" name="Route15" color="4" fill="6" visible="yes" active="no"/>
+<layer number="16" name="Bottom" color="1" fill="1" visible="yes" active="no"/>
+<layer number="17" name="Pads" color="2" fill="1" visible="yes" active="no"/>
+<layer number="18" name="Vias" color="2" fill="1" visible="yes" active="no"/>
+<layer number="19" name="Unrouted" color="6" fill="1" visible="yes" active="no"/>
+<layer number="20" name="Dimension" color="15" fill="1" visible="yes" active="no"/>
+<layer number="21" name="tPlace" color="7" fill="1" visible="yes" active="no"/>
+<layer number="22" name="bPlace" color="7" fill="1" visible="yes" active="no"/>
+<layer number="23" name="tOrigins" color="15" fill="1" visible="yes" active="no"/>
+<layer number="24" name="bOrigins" color="15" fill="1" visible="yes" active="no"/>
+<layer number="25" name="tNames" color="7" fill="1" visible="yes" active="no"/>
+<layer number="26" name="bNames" color="7" fill="1" visible="yes" active="no"/>
+<layer number="27" name="tValues" color="7" fill="1" visible="yes" active="no"/>
+<layer number="28" name="bValues" color="7" fill="1" visible="yes" active="no"/>
 <layer number="29" name="tStop" color="7" fill="3" visible="no" active="no"/>
 <layer number="30" name="bStop" color="7" fill="6" visible="no" active="no"/>
 <layer number="31" name="tCream" color="7" fill="4" visible="no" active="no"/>
@@ -44,8 +44,8 @@
 <layer number="34" name="bFinish" color="6" fill="6" visible="no" active="no"/>
 <layer number="35" name="tGlue" color="7" fill="4" visible="no" active="no"/>
 <layer number="36" name="bGlue" color="7" fill="5" visible="no" active="no"/>
-<layer number="37" name="tTest" color="7" fill="1" visible="no" active="no"/>
-<layer number="38" name="bTest" color="7" fill="1" visible="no" active="no"/>
+<layer number="37" name="tTest" color="7" fill="1" visible="yes" active="no"/>
+<layer number="38" name="bTest" color="7" fill="1" visible="yes" active="no"/>
 <layer number="39" name="tKeepout" color="4" fill="11" visible="no" active="no"/>
 <layer number="40" name="bKeepout" color="1" fill="11" visible="no" active="no"/>
 <layer number="41" name="tRestrict" color="4" fill="10" visible="no" active="no"/>
 <layer number="43" name="vRestrict" color="2" fill="10" visible="no" active="no"/>
 <layer number="44" name="Drills" color="7" fill="1" visible="no" active="no"/>
 <layer number="45" name="Holes" color="7" fill="1" visible="no" active="no"/>
-<layer number="46" name="Milling" color="3" fill="1" visible="no" active="no"/>
-<layer number="47" name="Measures" color="7" fill="1" visible="no" active="no"/>
-<layer number="48" name="Document" color="7" fill="1" visible="no" active="no"/>
-<layer number="49" name="Reference" color="7" fill="1" visible="no" active="no"/>
-<layer number="50" name="dxf" color="7" fill="1" visible="no" active="no"/>
-<layer number="51" name="tDocu" color="7" fill="1" visible="no" active="no"/>
-<layer number="52" name="bDocu" color="7" fill="1" visible="no" active="no"/>
-<layer number="53" name="tGND_GNDA" color="7" fill="1" visible="no" active="no"/>
-<layer number="54" name="bGND_GNDA" color="7" fill="1" visible="no" active="no"/>
-<layer number="56" name="wert" color="7" fill="1" visible="no" active="no"/>
-<layer number="57" name="tCAD" color="7" fill="1" visible="no" active="no"/>
+<layer number="46" name="Milling" color="3" fill="1" visible="yes" active="no"/>
+<layer number="47" name="Measures" color="7" fill="1" visible="yes" active="no"/>
+<layer number="48" name="Document" color="7" fill="1" visible="yes" active="no"/>
+<layer number="49" name="Reference" color="7" fill="1" visible="yes" active="no"/>
+<layer number="50" name="dxf" color="7" fill="1" visible="yes" active="no"/>
+<layer number="51" name="tDocu" color="7" fill="1" visible="yes" active="no"/>
+<layer number="52" name="bDocu" color="7" fill="1" visible="yes" active="no"/>
+<layer number="53" name="tGND_GNDA" color="7" fill="1" visible="yes" active="no"/>
+<layer number="54" name="bGND_GNDA" color="7" fill="1" visible="yes" active="no"/>
+<layer number="56" name="wert" color="7" fill="1" visible="yes" active="no"/>
+<layer number="57" name="tCAD" color="7" fill="1" visible="yes" active="no"/>
 <layer number="90" name="Modules" color="5" fill="1" visible="yes" active="yes"/>
 <layer number="91" name="Nets" color="2" fill="1" visible="yes" active="yes"/>
 <layer number="92" name="Busses" color="1" fill="1" visible="yes" active="yes"/>
@@ -12815,8 +12815,6 @@ diameter 3 mm, horizontal, grid 12.7 mm</description>
 <part name="R5" library="rcl" deviceset="R-EU_" device="R0805" value="100k"/>
 <part name="S+1" library="testpad" deviceset="TP" device="TP20SQ" value="TPTP20SQ"/>
 <part name="D4" library="diode" deviceset="ZENER-DIODE" device="SOD-123FL" value="5V"/>
-<part name="L" library="testpad" deviceset="TP" device="TP20SQ" value="TPTP20SQ"/>
-<part name="G" library="testpad" deviceset="TP" device="TP20SQ" value="TPTP20SQ"/>
 </parts>
 <sheets>
 <sheet>
@@ -12894,7 +12892,7 @@ Philipp Hachtmann</text>
 <instance part="GND11" gate="1" x="53.34" y="12.7"/>
 <instance part="P+20" gate="1" x="53.34" y="29.845"/>
 <instance part="LD1" gate="G$1" x="31.115" y="55.245"/>
-<instance part="GND8" gate="1" x="31.115" y="44.45"/>
+<instance part="GND8" gate="1" x="31.115" y="47.625"/>
 <instance part="R6" gate="G$1" x="31.115" y="62.865" rot="R90"/>
 <instance part="FRAME1" gate="G$1" x="0" y="0"/>
 <instance part="GND7" gate="1" x="63.5" y="103.505"/>
@@ -12908,8 +12906,6 @@ Philipp Hachtmann</text>
 <instance part="R5" gate="G$1" x="205.105" y="113.665" rot="R270"/>
 <instance part="S+1" gate="G$1" x="76.835" y="160.02" rot="R270"/>
 <instance part="D4" gate="G$1" x="83.185" y="116.84" rot="R90"/>
-<instance part="L" gate="G$1" x="22.225" y="68.58" rot="R90"/>
-<instance part="G" gate="G$1" x="21.59" y="57.15"/>
 </instances>
 <busses>
 </busses>
@@ -13049,12 +13045,6 @@ Philipp Hachtmann</text>
 <segment>
 <pinref part="GND8" gate="1" pin="GND"/>
 <pinref part="LD1" gate="G$1" pin="C"/>
-<wire x1="31.115" y1="46.99" x2="31.115" y2="48.895" width="0.1524" layer="91"/>
-<pinref part="G" gate="G$1" pin="TP"/>
-<wire x1="31.115" y1="48.895" x2="31.115" y2="50.165" width="0.1524" layer="91"/>
-<wire x1="21.59" y1="54.61" x2="21.59" y2="48.895" width="0.1524" layer="91"/>
-<wire x1="21.59" y1="48.895" x2="31.115" y2="48.895" width="0.1524" layer="91"/>
-<junction x="31.115" y="48.895"/>
 </segment>
 <segment>
 <wire x1="205.105" y1="105.41" x2="220.345" y2="105.41" width="0.1524" layer="91"/>
@@ -13222,12 +13212,8 @@ Philipp Hachtmann</text>
 </segment>
 <segment>
 <pinref part="R6" gate="G$1" pin="2"/>
-<wire x1="31.115" y1="67.945" x2="31.115" y2="68.58" width="0.1524" layer="91"/>
+<wire x1="31.115" y1="67.945" x2="31.115" y2="73.025" width="0.1524" layer="91"/>
 <label x="31.115" y="73.025" size="1.27" layer="95" rot="R90" xref="yes"/>
-<pinref part="L" gate="G$1" pin="TP"/>
-<wire x1="31.115" y1="68.58" x2="31.115" y2="73.025" width="0.1524" layer="91"/>
-<wire x1="24.765" y1="68.58" x2="31.115" y2="68.58" width="0.1524" layer="91"/>
-<junction x="31.115" y="68.58"/>
 </segment>
 </net>
 <net name="N$2" class="0">
index 07546bdf97d8e857eb0de139d0ed6568c5a60c92..e8e59d2affda1cca890b6f64bca21d7a71c3cff5 100644 (file)
@@ -27,7 +27,7 @@
 # To rebuild project do "make clean" then "make all".
 #----------------------------------------------------------------------------
 
-CONFIG?=trennfix_attiny25
+CONFIG?=trennfix_0.4
 
 include mk/${CONFIG}.mk
 
@@ -216,7 +216,7 @@ AVRDUDE_FLAGS = -p $(MCU) -P $(AVRDUDE_PORT) -c $(AVRDUDE_PROGRAMMER)
 AVRDUDE_FLAGS += $(AVRDUDE_NO_VERIFY)
 AVRDUDE_FLAGS += $(AVRDUDE_VERBOSE)
 AVRDUDE_FLAGS += $(AVRDUDE_ERASE_COUNTER)
-AVRDUDE_FLAGS += -B 20
+AVRDUDE_FLAGS += -B 2
 
 
 #---------------- Debugging Options ----------------
index 4f07b0b0310e5f8531773ab66afb184d01d16f0c..71542819067e764839b425d9d7f403c56552e0e3 100644 (file)
@@ -1,10 +1,7 @@
 #ifndef   __HARDWARE_H_GENERIC__
 #define __HARDWARE_H_GENERIC__
 
-
-#include __HW_CONF_HEADER__
-
-
+#include <config/trennfix_0.4.h>
 
 
 #endif
diff --git a/trennfix/sw/config/trennfix_0.4.h b/trennfix/sw/config/trennfix_0.4.h
new file mode 100644 (file)
index 0000000..964853e
--- /dev/null
@@ -0,0 +1,81 @@
+#ifndef __HARDWARE_H
+#define __HARDWARE_H
+
+#include <pin_magic.h>
+
+#define PIN_LED   _PIN(PORTB, PORTB2)
+#define PIN_SENSE _PIN(PORTB, PORTB4)
+#define PIN_DRIVE _PIN(PORTB, PORTB3)
+//#define PIN_DRIVE PIN_LED
+#define PIN_BTN   _PIN(PORTB, PB1)
+
+#define BTN_PRESSED (!PINVAL(PIN_BTN))
+
+#define START_TIMER0 ({TCNT0 = 0; TCCR0B = 2;})
+#define START_TIMER1 ({TCNT1 = 1; TCCR1 = 7; GTCCR |= 2;})
+#define STOP_TIMER1 ({TCCR1 = 0; TCNT1 = 1;})
+
+static inline void setup_hw(void)
+{
+       /* Turn off the 1/8 clock prescaler - now running at 16MHz*/
+       CLKPR = (1 << CLKPCE);
+       CLKPR = 0;
+
+       INPUT_PIN(PIN_SENSE);
+       INPUT_PIN(PIN_BTN);
+       OUTPUT_PIN(PIN_DRIVE);
+       OUTPUT_PIN(PIN_LED);
+       setpin(PIN_BTN, 1);   /* Need pullup              */
+       
+       GIMSK |= _BV(PCIE);     /* Enable pin change interrupt for sense port */
+       PCMSK |= _BV(PCINT4);    /* PB4, Rail sense input */
+
+       /* Change interrupt for button */
+       PCMSK |= _BV(PCINT1);    /* PB1 */
+
+       /* Setup timer 0, used for mm_switch */
+        TCCR0A = 0; /* Normal mode */
+       TCCR0B = 0; /* Timer off */
+       TIMSK |= _BV(OCIE0A);   /* Get a match interrupt */
+
+#ifdef WITH_PWM        
+       /* Timer 1 as PWM */
+       OCR1C = 14;
+       OCR1B = 14;
+       TCCR1 = 0x6;
+       GTCCR |= _BV(PWM1B) | _BV(COM1B0);
+#endif
+
+}
+
+/*
+ * Function to trigger an oscilloscope on the drive pin
+ *
+ * Can be altered to use the LED.
+ *
+ */
+static void __attribute__((unused)) trigger(void)
+{
+       setpin(PIN_DRIVE, 1);
+       _delay_us(4);
+       setpin(PIN_DRIVE, 0);
+       _delay_us(4);
+}
+
+/*
+ * Configuration for mm receiver code.
+ */
+
+#define MM_SENSE (!PINVAL(PIN_SENSE))
+#define MM_TSTART ({TCNT0 = 0; GTCCR |= 1; OCR0A = 115; TCCR0B = 2;})
+#define MM_TIMER_INT_VECT TIMER0_COMPA_vect
+
+/* Costs 38 bytes program memory */
+#define MM_FILTER_REPEATED
+#define USE_EEPROM_UPDATE
+
+#ifdef USE_REGISTER_VARS
+uint8_t register drive_on asm("r8");
+#endif
+
+#endif
diff --git a/trennfix/sw/config/trennfix_attiny25.h b/trennfix/sw/config/trennfix_attiny25.h
deleted file mode 100644 (file)
index c733c71..0000000
+++ /dev/null
@@ -1,87 +0,0 @@
-#ifndef __HARDWARE_H
-#define __HARDWARE_H
-
-#include <pin_magic.h>
-
-#define PIN_LED   _PIN(PORTB, PORTB2)
-#define PIN_SENSE _PIN(PORTB, PORTB4)
-//#define PIN_DRIVE _PIN(PORTB, PORTB3)
-#define PIN_DRIVE PIN_LED
-#define PIN_BTN   _PIN(PORTB, PB1)
-
-#define BTN_PRESSED (!PINVAL(PIN_BTN))
-
-#define START_TIMER0 ({TCNT0 = 0; TCCR0B = 2;})
-#define START_TIMER1 ({TCNT1 = 1; TCCR1 = 7; GTCCR |= 2;})
-#define STOP_TIMER1 ({TCCR1 = 0; TCNT1 = 1;})
-
-
-/*
- * Various sinks for valuable program memory
- *
- */
-// #define USE_EEPROM_UPDATE /* 14 bytes */
-//#define INTERPRET_DRIVE_COMMANDS
-#define INTERPRET_DRIVE_SIMPLE
-
-static inline void setup_hw(void)
-{
-       /* Turn off the 1/8 clock prescaler - now running at 16MHz*/
-       CLKPR = (1 << CLKPCE);
-       CLKPR = 0;
-
-       INPUT_PIN(PIN_SENSE);
-       INPUT_PIN(PIN_BTN);
-       OUTPUT_PIN(PIN_DRIVE);
-       OUTPUT_PIN(PIN_LED);
-       setpin(PIN_BTN, 1);   /* Need pullup              */
-       
-       GIMSK |= _BV(PCIE);     /* Enable pin change interrupt for sense port */
-       PCMSK |= _BV(PCINT4);    /* PB4, Rail sense input */
-
-       /* Change interrupt for button */
-       PCMSK |= _BV(PCINT1);    /* PB1 */
-
-       /* Setup timer 0, used for mm_switch */
-        TCCR0A = 0; /* Normal mode */
-       TCCR0B = 0; /* Timer off */
-       TIMSK |= _BV(OCIE0A);   /* Get a match interrupt */
-       
-       /* We need 13 + 45,5 us delay, That's 464 clocks @8MHz*/
-       //OCR0A = 91; /* Prescaler 8 is used */
-
-       /* Timer 1 for timeout */
-       /* We set it to 1024us by prescaler 64 and running full 256 */
-       // TCCR1 = 7;
-       //      TIMSK |= _BV(TOIE1); /* Overflow interrupt */
-}
-
-/*
- * Function to trigger an oscilloscope on the drive pin
- *
- * Can be altered to use the LED.
- *
- */
-static void __attribute__((unused)) trigger(void)
-{
-       setpin(PIN_DRIVE, 1);
-       _delay_us(4);
-       setpin(PIN_DRIVE, 0);
-       _delay_us(4);
-}
-
-/*
- * Configuration for mm receiver code.
- */
-
-#define MM_SENSE (!PINVAL(PIN_SENSE))
-#define MM_TSTART_FAST ({TCNT0 = 0; GTCCR |= 1; OCR0A = 120; TCCR0B = 2;})
-#define MM_TSTART_SLOW ({TCNT0 = 0; GTCCR |= 1; OCR0A = 230; TCCR0B = 2;})
-#define MM_TSTOP ({TCCR0B = 0;})
-#define MM_TIMER_INT_VECT TIMER0_COMPA_vect
-
-/* Costs 63 bytes program memory */
-#define MM_FILTER_REPEATED
-
-#define USE_EEPROM_UPDATE
-#endif
diff --git a/trennfix/sw/config/trennfix_attiny85.h b/trennfix/sw/config/trennfix_attiny85.h
deleted file mode 100644 (file)
index 39c1592..0000000
+++ /dev/null
@@ -1,85 +0,0 @@
-#ifndef __HARDWARE_H
-#define __HARDWARE_H
-
-#include <pin_magic.h>
-
-#define PIN_LED   _PIN(PORTB, PORTB2)
-#define PIN_SENSE _PIN(PORTB, PORTB4)
-#define PIN_DRIVE _PIN(PORTB, PORTB3)
-#define PIN_BTN   _PIN(PORTB, PB1)
-
-#define BTN_PRESSED (!PINVAL(PIN_BTN))
-
-#define START_TIMER0 ({TCNT0 = 0; TCCR0B = 2;})
-#define START_TIMER1 ({TCNT1 = 1; TCCR1 = 7; GTCCR |= 2;})
-#define STOP_TIMER1 ({TCCR1 = 0; TCNT1 = 1;})
-
-
-/*
- * Various sinks for valuable program memory
- *
- */
-// #define USE_EEPROM_UPDATE /* 14 bytes */
-//#define INTERPRET_DRIVE_COMMANDS
-#define INTERPRET_DRIVE_SIMPLE
-
-static inline void setup_hw(void)
-{
-       /* Turn off the 1/8 clock prescaler - now running at 16MHz*/
-       CLKPR = (1 << CLKPCE);
-       CLKPR = 0;
-
-       INPUT_PIN(PIN_SENSE);
-       INPUT_PIN(PIN_BTN);
-       OUTPUT_PIN(PIN_DRIVE);
-       OUTPUT_PIN(PIN_LED);
-       setpin(PIN_BTN, 1);   /* Need pullup              */
-       
-       GIMSK |= _BV(PCIE);     /* Enable pin change interrupt for sense port */
-       PCMSK |= _BV(PCINT4);    /* PB4, Rail sense input */
-
-       /* Change interrupt for button */
-       PCMSK |= _BV(PCINT1);    /* PB1 */
-
-       /* Setup timer 0, used for mm_switch */
-        TCCR0A = 0; /* Normal mode */
-       TCCR0B = 0; /* Timer off */
-       TIMSK |= _BV(OCIE0A);   /* Get a match interrupt */
-       
-       /* We need 13 + 45,5 us delay, That's 464 clocks @8MHz*/
-       //OCR0A = 91; /* Prescaler 8 is used */
-
-       /* Timer 1 for timeout */
-       /* We set it to 1024us by prescaler 64 and running full 256 */
-       // TCCR1 = 7;
-       //      TIMSK |= _BV(TOIE1); /* Overflow interrupt */
-}
-
-/*
- * Function to trigger an oscilloscope on the drive pin
- *
- * Can be altered to use the LED.
- *
- */
-static void __attribute__((unused)) trigger(void)
-{
-       setpin(PIN_DRIVE, 1);
-       _delay_us(4);
-       setpin(PIN_DRIVE, 0);
-       _delay_us(4);
-}
-
-/*
- * Configuration for mm receiver code.
- */
-
-#define MM_SENSE (!PINVAL(PIN_SENSE))
-#define MM_TSTART_FAST ({TCNT0 = 0; GTCCR |= 1; OCR0A = 110; TCCR0B = 2;})
-#define MM_TSTART_SLOW ({TCNT0 = 0; GTCCR |= 1; OCR0A = 220; TCCR0B = 2;})
-#define MM_TSTOP ({TCCR0B = 0;})
-#define MM_TIMER_INT_VECT TIMER0_COMPA_vect
-
-/* Costs 63 bytes program memory */
-#define MM_FILTER_REPEATED
-
-#endif
diff --git a/trennfix/sw/include/pin_magic.h b/trennfix/sw/include/pin_magic.h
new file mode 100644 (file)
index 0000000..a6d0b4b
--- /dev/null
@@ -0,0 +1,23 @@
+#ifndef __HACHTIS_PIN_MAGIC_H
+#define __HACHTIS_PIN_MAGIC_H
+
+#include <avr/io.h>
+
+struct __ph_pin__ {
+       volatile uint8_t *addr;
+       uint8_t bitno;
+};
+
+#define _PIN(port, bit) ((volatile struct __ph_pin__){&port, bit})
+
+#define OUTPUT_PIN(pin) (*(pin.addr - 1) |= _BV(pin.bitno))
+#define INPUT_PIN(pin)  (*(pin.addr - 1) &= ~_BV(pin.bitno))
+
+#define PINON(pin)   (*pin.addr  |= _BV(pin.bitno))
+#define PINOFF(pin)  (*pin.addr  &= ~_BV(pin.bitno))
+
+#define PINVAL(pin)  (*(pin.addr - 2) & _BV(pin.bitno) ? 1 : 0)
+
+#define setpin(pin, val) ((val) ? PINON(pin) : PINOFF(pin))
+
+#endif
diff --git a/trennfix/sw/mk/trennfix_0.4.mk b/trennfix/sw/mk/trennfix_0.4.mk
new file mode 100644 (file)
index 0000000..27d0204
--- /dev/null
@@ -0,0 +1,35 @@
+
+SRC = src/main.c
+
+################################################################################
+################################################################################
+
+AVRDUDE_PROGRAMMER = avrisp2
+MCU?=attiny25
+F_CPU = 16000000
+
+# Fuse-Bits gibts praktisch bei http://www.engbedded.com/fusecalc !
+# 8 MHz interner RC-Oszillator usw. Brown out 4V
+
+ifneq ($(KEEP_EEPROM),)
+
+HFUSE=0xd4
+
+else
+
+HFUSE=0xdc
+
+endif
+
+LFUSE=0x61
+EFUSE=0xff
+
+#CFLAGS+= -DMM_FILTER_REPEATED
+CFLAGS+= -DMM_USE_REGISTER_VARS
+
+CFLAGS+= -DUSE_REGISTER_VARS
+CFLAGS+= -DWITH_EEPROM_UPDATE
+CFLAGS+= -DWITH_PWM
+CFLAGS+= -DWITH_SOUND
+CFLAGS+= -DWITH_INITIAL_PULSE
+
diff --git a/trennfix/sw/mk/trennfix_attiny25.mk b/trennfix/sw/mk/trennfix_attiny25.mk
deleted file mode 100644 (file)
index 64cd1ad..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-
-SRC = src/main.c
-
-################################################################################
-################################################################################
-
-AVRDUDE_PROGRAMMER = avrisp2
-MCU=attiny25
-F_CPU = 16000000
-
-# Fuse-Bits gibts praktisch bei http://www.engbedded.com/fusecalc !
-# 8 MHz interner RC-Oszillator usw. Brown out 4V
-
-ifneq ($(KEEP_EEPROM),)
-
-HFUSE=0xd4
-
-else
-
-HFUSE=0xdc
-
-endif
-
-LFUSE=0x61
-EFUSE=0xff
-
-CFLAGS+=-DONLY_2K -DMM_USE_REGISTER_VARS
-
-
-
-
-
-
-
-
-
-
diff --git a/trennfix/sw/mk/trennfix_attiny85.mk b/trennfix/sw/mk/trennfix_attiny85.mk
deleted file mode 100644 (file)
index fe044a8..0000000
+++ /dev/null
@@ -1,41 +0,0 @@
-
-SRC = src/main.c
-
-
-################################################################################
-################################################################################
-
-AVRDUDE_PROGRAMMER = avrisp2
-MCU=attiny85
-F_CPU = 16000000
-
-# Fuse-Bits gibts praktisch bei http://www.engbedded.com/fusecalc !
-# 8 MHz interner RC-Oszillator usw. Brown out 4V
-
-
-#LFUSE=0x61
-#HFUSE=0xdc
-#EFUSE=0xff
-
-LFUSE=0x61
-
-ifneq ($(KEEP_EEPROM),)
-
-HFUSE=0xd4
-
-else
-
-HFUSE=0xdc
-
-endif
-
-EFUSE=0xff
-
-
-
-
-
-
-
-
-
index ba68a8b92354319fba7eec165bfae9495de962bd..4be3e3652f2d34afc64a255384eeab691e74f7e0 100644 (file)
  * Check for stuff we need
  *
  */
-#if !defined(MM_TSTART_FAST) || !defined(MM_TSTART_SLOW) || !defined(MM_TSTOP) \
-       || !defined(MM_SENSE) || !defined(MM_TIMER_INT_VECT)
+#if !defined(MM_TSTART) || !defined(MM_SENSE) || !defined(MM_TIMER_INT_VECT)
 
-#error Missing timer start macro MM_TSTART_FAST!
+#error Missing needed MM_... macro!
 
 #endif
 
@@ -233,18 +232,17 @@ ISR(MM_TIMER_INT_VECT) {
        uint8_t address;
        uint8_t command;
 
-       MM_TSTART_FAST;
-
 #ifdef MM_FILTER_REPEATED
        static uint8_t address_last = 0xff;
        static uint8_t function_last = 0xff;
        static uint8_t command_last = 0xff;
 #endif
 
+       MM_TSTART;
+
        switch(recstate) {
-       
        case MM_FIRST_FAST_SAMPLE:
-               recstate = MM_FIRST_SLOW_SAMPLE      ;
+               recstate = MM_FIRST_SLOW_SAMPLE;
                break;
 
        case MM_FIRST_SLOW_SAMPLE:
@@ -277,6 +275,7 @@ ISR(MM_TIMER_INT_VECT) {
 
        case MM_SLOW_WAIT_FOR_CLOCK:
                if (mm_rec_tolerated_timeouts) {
+                       trigger();
                        mm_rec_tolerated_timeouts--;
                        recstate = MM_SLOW_WAIT_FOR_CLOCK_DELAY;
                        return;
@@ -295,6 +294,7 @@ ISR(MM_TIMER_INT_VECT) {
                shift_function_first = shift_function;
                shift_command_first  = shift_command;
                mm_rec_tolerated_timeouts = 18;
+               trigger();
        } 
 
        if (bitno == 36) {
@@ -368,7 +368,7 @@ void mm_pinchange_handler(void)
        if (!sense_last)
                return;
 
-       MM_TSTART_FAST;
+       MM_TSTART;
 
        switch(recstate) {
        case MM_IDLE:
@@ -394,6 +394,9 @@ void mm_pinchange_handler(void)
                mm_rec_tolerated_timeouts = 0;
                break;
 
+       case MM_SLOW_SAMPLE_DELAY:
+               recstate = MM_SLOW_SAMPLE;
+               break;
                /* Not expected */
        case MM_FIRST_FAST_SAMPLE:
        case MM_FAST_SAMPLE:
diff --git a/trennfix/sw/pin_magic.h b/trennfix/sw/pin_magic.h
deleted file mode 100644 (file)
index a6d0b4b..0000000
+++ /dev/null
@@ -1,23 +0,0 @@
-#ifndef __HACHTIS_PIN_MAGIC_H
-#define __HACHTIS_PIN_MAGIC_H
-
-#include <avr/io.h>
-
-struct __ph_pin__ {
-       volatile uint8_t *addr;
-       uint8_t bitno;
-};
-
-#define _PIN(port, bit) ((volatile struct __ph_pin__){&port, bit})
-
-#define OUTPUT_PIN(pin) (*(pin.addr - 1) |= _BV(pin.bitno))
-#define INPUT_PIN(pin)  (*(pin.addr - 1) &= ~_BV(pin.bitno))
-
-#define PINON(pin)   (*pin.addr  |= _BV(pin.bitno))
-#define PINOFF(pin)  (*pin.addr  &= ~_BV(pin.bitno))
-
-#define PINVAL(pin)  (*(pin.addr - 2) & _BV(pin.bitno) ? 1 : 0)
-
-#define setpin(pin, val) ((val) ? PINON(pin) : PINOFF(pin))
-
-#endif
index 47d051d34dacce3e486d21da22a6256932cea3d7..c61741e6b22632ba2ac997c58a2a33952dffb54f 100644 (file)
@@ -44,12 +44,16 @@ enum op_mode {
 
 enum learn_mode {
        LM_OFF = 0,
-       LM_LEARN_ON_KEY,   /* Learn primary key                           */
-       LM_LEARN_OFF_KEY,  /* Learn secondary key, relevant for OM_DOUBLE */
-       LM_LEARN_INITIAL,  /* Learn initial pulse length, 10ms steps      */
-       LM_LEARN_DUTY,     /* Learn duty cycle 0-10                       */
-       LM_LEARN_OP_MODE,  /* Learn operation mode                        */
-       LM_END,            /* Only a label                                */
+       LM_LEARN_ON_KEY,     /* Learn primary key                           */
+       LM_LEARN_OFF_KEY,    /* Learn secondary key, relevant for OM_DOUBLE */
+       LM_LEARN_INITIAL,    /* Learn initial pulse length, 10ms steps      */
+       LM_LEARN_DUTY,       /* Learn duty cycle 0-10                       */
+       LM_LEARN_OP_MODE,    /* Learn operation mode                        */
+       LM_EASY_WAIT_PRESS,  /* Wait for key press to enter easy mode       */
+       LM_EASY_WAIT_UP,     /* Wait for end of key press                   */
+       LM_EASY_WAIT_TURN,   /* Wait for loco 80 turn end                   */
+       LM_EASY_MODE,        /* Easy config mode for PWM and initial kick   */
+       LM_END,              /* Only a label                                */
 };             
 
 struct config {
@@ -66,7 +70,86 @@ struct config {
 
 static struct EEMEM config ee_config;
 static volatile struct config config;
+
+static volatile uint8_t easy_mode = 0;
+static volatile uint8_t easy_mode_possible = 0;
+
+#ifndef USE_REGISTER_VARS
 static volatile uint8_t drive_on = 0;
+#endif
+
+/******************************************************************************
+ *
+ * Some nice sounds to play on your coil
+ *
+ */
+
+#define G 180
+#define sekunde(g)(quinte((quinte(g)))*2)
+#define terz(g) ((g) * 4 / 5)
+#define kleine_terz(g) ((g) * 5 / 6)
+#define quarte(g) ((g) * 3 / 4)
+#define quinte(g) ((g) * 2 / 3)
+#define tt(g) ((g) * 32 / 45)
+#define septime(g) ((g) * 15 / 8)
+
+#if defined(WITH_SOUND) && defined(WITH_PWM)
+void play_tone(uint8_t divisor, uint8_t duration, uint8_t pause)
+{
+       uint16_t c;
+       TCCR1 = 0x8;
+       OCR1C = divisor;
+       OCR1B = divisor / 2;
+       for (c = 0; c < duration - pause; c++)
+               _delay_ms(2);
+       OCR1B = 255;
+       OCR1C = 14;
+       for (c = 0; c < pause; c++)
+               _delay_ms(2);
+       TCCR1 = 0x6;
+       OCR1C = 14;
+       OCR1B = 14;
+}
+
+static void tone_enter(void)
+{
+       play_tone((G), 70, 20);
+       play_tone(terz(G), 70, 20);
+       play_tone(quinte(G), 70, 20);
+       play_tone(G/2, 100, 0);
+}
+
+static void tone_good(void)
+{
+       play_tone(G, 150, 120);
+       play_tone(terz(G), 100, 70);
+       play_tone(tt(G), 100, 50);
+       play_tone(quarte(terz((G))), 50, 0);
+       play_tone(quinte(G), 150, 0);
+       play_tone(terz(G), 100, 50);            
+}
+
+static void snd_on(void)
+{
+       TCCR1 = 0x8;
+       OCR1C = 120;
+       OCR1B = 60;
+}
+
+static void snd_off(void)
+{
+       TCCR1 = 0x6;
+       OCR1C = 14;
+       OCR1B = 14;
+}
+
+#else
+#define play_tone(...)
+#define tone_enter(...)
+#define tone_good(...)
+#define snd_on(...)
+#define snd_off(...)
+#endif
 
 static void load_config(void)
 {
@@ -75,15 +158,13 @@ static void load_config(void)
 
 static void save_config(void)
 {
-#ifdef USE_EEPROM_UPDATE
+#ifdef WITH_EEPROM_UPDATE
        eeprom_update_block((uint8_t *)&config, &ee_config, sizeof(config));
 #else
        eeprom_write_block((uint8_t *)&config, &ee_config, sizeof(config));
 #endif
 }
 
-
-
 ISR(PCINT0_vect){
        static uint8_t btn_last = 0;
 
@@ -101,13 +182,9 @@ static uint8_t get_speed(uint8_t command)
        uint8_t b1,  b3, b5, b7;
                
        b1 = ((command & 0x80) != 0);
-       //      b2 = ((command & 0x40) != 0);
        b3 = ((command & 0x20) != 0);
-       //      b4 = ((command & 0x10) != 0);
        b5 = ((command & 0x8) != 0);
-       //      b6 = ((command & 0x4) != 0);
        b7 = ((command & 0x2) != 0);
-       //      b8 = ((command & 0x1) != 0);
        
        //if ((b1 != b2) || (b2 != b3) || (b3 != b4) || (b5 != b6) || (b7 != b8))
        //      return 0xff;
@@ -115,96 +192,58 @@ static uint8_t get_speed(uint8_t command)
        return (b1 + b3*2 + b5*4 +b7*8);
 }
 
-#ifdef INTERPRET_DRIVE_COMMANDS
 
-void mm_switch_drive(uint8_t decoder, uint8_t function, uint8_t command)
+void mm_switch_drive(uint8_t loco, uint8_t function, uint8_t command)
 {
-       static uint8_t seen_before = 0;
        uint8_t speed;
-
-       if (!seen_before) {
-               if ((decoder == 80) && (function == 0) && (command == 0xc0)) {
-                       config.learn_mode = 1;
-                       save_config();
-               }
-       }
-       seen_before = 1;
-       
        speed = get_speed(command);
-       static uint8_t itsme = 0;
-
-       if (config.learn_mode) {
-               if (decoder == 70) {
-                       if (speed == 1) {
-                               itsme = 1;
-                       drive_on = 1;
-                       }else {
-                               if (itsme) {
-                                       drive_on = 0;
-                                       itsme = 0;
-                               }
-                       }
-               }
-               
-               if (decoder == 33) {
-                       if (speed != 0xff) {
-                               if (speed >= 1) speed -= 1;
-                               if (speed <= 14)
-                                       config.on_duty_cycle = speed;
-                               else
-                                       config.on_duty_cycle = 14;
-                               
-                       }
-               }
-               
-               if (decoder == 32) {
-                       if (speed != 0xff) {
-                               config.initial_pulse = speed;
+       static uint8_t alert_last = 0;
+
+       switch(loco) {
+       case 80:
+               switch (config.learn_mode) {
+               case LM_OFF:
+                       if (speed == 1)
+                               config.learn_mode = LM_EASY_WAIT_PRESS;
+                       break;
+               case LM_EASY_MODE:
+                       if ((speed == 1) && (alert_last == 0)) {
+                               config.learn_mode = LM_OFF;
+                               save_config();
+                               tone_good();
                        }
-               }
-               
-               if (decoder == 31 && command == 0xc0)
-                       save_config();
-       }
-}
-
-#else
-#ifdef INTERPRET_DRIVE_SIMPLE
+                       break;
 
-static volatile uint8_t current_loco;
+               case LM_EASY_WAIT_PRESS:
+                       if (speed != 1)
+                           config.learn_mode = LM_OFF;
+                       break;
 
-void mm_switch_drive(uint8_t decoder, uint8_t function, uint8_t command)
-{
-       uint8_t speed;
-       speed = get_speed(command);
-       current_loco = decoder;
-       if (speed != 0xff) {
-               if (decoder == 50) {
-                       setpin(PIN_LED, drive_on = function & 3);
+               default:
+                       break;
+               }
+               alert_last = (speed == 1);
+               break;
+       case 50:
+               if (speed)
+                       speed -= 1;
+               
+               if (config.learn_mode == LM_EASY_MODE) {
                        config.initial_pulse = speed;
-               } else if (decoder == 51) {
-                       if (speed >= 1) speed -= 1;
-                       if (speed <= 14)
-                               config.on_duty_cycle = speed;
-                       else
-                               config.on_duty_cycle = 14;
-               } else if (decoder == 52) {
-                       static uint8_t last_speed;
-                       if (speed == 1 && last_speed != 1)
-                               save_config();
-                       last_speed = speed;
-                       
                }
+               break;
+       case 51:
+               if (config.learn_mode == LM_EASY_MODE)
+                       config.on_duty_cycle = speed;
+               break;
        }
+       
 }
 
-#endif
-#endif
-static volatile uint8_t switch_on = 0;
-
 void mm_switch_command(uint8_t decoder, uint8_t command)
 {
        static uint8_t toggle_lock = 0;
+
        switch(config.learn_mode) {
 
        case LM_OFF:
@@ -214,13 +253,11 @@ void mm_switch_command(uint8_t decoder, uint8_t command)
                        switch(config.op_mode) {
                        case OM_MOMENTARY:
                        case OM_DOUBLE:
-                               if (!switch_on && current_loco == 52)
-                                       save_config();
-                               switch_on = 1;
+                               drive_on = 1;
                                break;
                        case OM_TOGGLE:
                                if (!toggle_lock) {
-                                       drive_on = !drive_on;
+                                       drive_on = ~drive_on;
                                        toggle_lock = 1;
                                }
                                break;
@@ -228,12 +265,11 @@ void mm_switch_command(uint8_t decoder, uint8_t command)
                                break;
                        }
                }
-
                if ((decoder == config.decoder_on) &&
                    (command == 0)) {  /* Primary key released */
                        switch(config.op_mode) {
                        case OM_MOMENTARY:
-                               switch_on = 0;
+                               drive_on = 0;
                                break;
                        case OM_TOGGLE:
                                toggle_lock = 0;
@@ -242,6 +278,22 @@ void mm_switch_command(uint8_t decoder, uint8_t command)
                                break;
                        }
                }
+               break;
+
+       case LM_EASY_WAIT_PRESS:
+               if ((decoder == config.decoder_on) &&
+                   (command == config.key_on))
+                       config.learn_mode = LM_EASY_WAIT_UP;
+               return;
+
+       case LM_EASY_WAIT_UP:
+               if ((decoder == config.decoder_on) &&
+                   (command == 0)) {
+                       config.learn_mode = LM_EASY_MODE;
+                       tone_enter();
+               }
+               return;
+       
 #ifdef HANDLE_OFF_KEY
 
                if ((decoder == config.decoder_off) &&
@@ -366,18 +418,33 @@ void mm_switch_command(uint8_t decoder, uint8_t command)
  */
 void shift(uint8_t mu);
 
+#ifdef WITH_PWM
+#define DRIVE_OFF  {OCR1B = 14;}
+#define DRIVE_ON   {OCR1B = 14 - config.on_duty_cycle;}
+#define DRIVE_FULL {OCR1B = 0;}
+#else
+#define DRIVE_OFF  {setpin(PIN_DRIVE, 0);}
+#define DRIVE_ON   {setpin(PIN_DRIVE, 1); setpin(PIN_LED, 1);}
+#define DRIVE_FULL {setpin(PIN_DRIVE, 1); setpin(PIN_LED, 0);}
+#endif
+
 int main(void) {
-       uint8_t learn_mode_off;
+       uint16_t i;
+
+#ifdef WITH_INITIAL_PULSE
        uint8_t drive_last = 0;
        uint8_t drive_slope = 0;
-       uint8_t i;
-       uint8_t output_on;
+#endif
+
 
+#ifdef USE_REGISTER_VARS
+       drive_on = 0;
+#endif
        mm_init();
        load_config();
        setup_hw();
-       
-       if ((config.op_mode == OM_ERASED) || (config.magic != EE_MAGIC)) {
+
+       if (config.magic != EE_MAGIC) {
                config.magic = EE_MAGIC;
                config.op_mode = OM_MOMENTARY;
                config.decoder_on = 1;
@@ -388,81 +455,59 @@ int main(void) {
                config.on_duty_cycle = 5;
                config.learn_mode = LM_LEARN_ON_KEY;
        }
-       drive_on = 0;
        sei();
 
-
-       //setpin(PIN_LED,1 );
-       //_delay_ms(400);
-       //setpin(PIN_LED,0 );
        while (1) {
-               
        drive_start:
 
-               output_on = drive_on || switch_on;
+#ifdef WITH_INITIAL_PULSE
                cli();
-               if (!drive_last && output_on)
+               if (drive_on && !drive_last)
                        drive_slope = 1;
                else
                        drive_slope = 0;
-               drive_last = output_on;
+               drive_last = drive_on;
                sei();
+#endif
+               if (drive_on) {
 
-               if (output_on) {
+#ifdef WITH_INITIAL_PULSE
                        if (drive_slope) {
+                               DRIVE_FULL;
                                for (i = 0; i < config.initial_pulse; i++) {
-                                       setpin(PIN_DRIVE, 1);   
-                                       _delay_ms(20);
+                                       _delay_ms(5);
                                }
                        }
-
-                       for (i = 0; i < config.on_duty_cycle; i++) {
-                               setpin(PIN_DRIVE, output_on);
-                               _delay_us(1);
-                       }
-                       for (i = 0; i < (14 - config.on_duty_cycle); i++) {
-                               setpin(PIN_DRIVE, 0);
-                               _delay_us(1);
-                       }
-
+#endif
+                       DRIVE_ON;
+               
                } else {
-                       setpin(PIN_DRIVE, 0);
-                       if (!config.learn_mode)
+                       DRIVE_OFF;
+
+                       if (!config.learn_mode ||
+                           config.learn_mode > LM_LEARN_OP_MODE)
                                continue;
 
-                       learn_mode_off = !config.learn_mode;
-                       
-                       if (output_on || (config.learn_mode && learn_mode_off))
-                               goto drive_start;
 
                        for (i = 0; i < config.learn_mode; i++) {
                                setpin(PIN_LED, 1);
+                               snd_on();
                                _delay_ms(10);
-                               //if (output_on || (config.learn_mode && learn_mode_off))
-                               //      goto drive_start;
                                setpin(PIN_LED, 0);
+                               snd_off();
+                               if (drive_on) goto drive_start;
                                _delay_ms(135);
-                               //if (output_on || (config.learn_mode && learn_mode_off))
-                               //      goto drive_start;
-
-                               //if (output_on || (config.learn_mode && learn_mode_off))
-                               //      goto drive_start;
+                               if (drive_on) goto drive_start;
                        }
                        for (i = 0; i < 15 - config.learn_mode; i++) {
-                               //if (output_on || (config.learn_mode && learn_mode_off))
-                               //      goto drive_start;
-                               setpin(PIN_LED, 0);
+                               if (drive_on) goto drive_start;
                                _delay_ms(70);
-                               //if (output_on || (config.learn_mode && learn_mode_off))
-                               //      goto drive_start;
-                               // _delay_ms(40);
                        }
                }
        }
        return 0;
 }
 
-
 /******************************************************************************
  *                        The end :-)
  */