diff --git a/bitlair_doorduino.code-workspace b/bitlair_doorduino.code-workspace deleted file mode 100644 index 2499b26..0000000 --- a/bitlair_doorduino.code-workspace +++ /dev/null @@ -1,20 +0,0 @@ -{ - "folders": [ - { - "path": "." - }, - { - "path": "bitlair_doorduino" - }, - { - "path": "bitlair_doorduino_inner" - }, - { - "path": "bitlair_doorduino_door" - }, - { - "path": "reset_eeprom" - } - ], - "settings": {} -} diff --git a/bitlair_doorduino_door/.gitignore b/bitlair_doorduino_door/.gitignore deleted file mode 100644 index 89cc49c..0000000 --- a/bitlair_doorduino_door/.gitignore +++ /dev/null @@ -1,5 +0,0 @@ -.pio -.vscode/.browse.c_cpp.db* -.vscode/c_cpp_properties.json -.vscode/launch.json -.vscode/ipch diff --git a/bitlair_doorduino_door/.vscode/extensions.json b/bitlair_doorduino_door/.vscode/extensions.json deleted file mode 100644 index 080e70d..0000000 --- a/bitlair_doorduino_door/.vscode/extensions.json +++ /dev/null @@ -1,10 +0,0 @@ -{ - // See http://go.microsoft.com/fwlink/?LinkId=827846 - // for the documentation about the extensions.json format - "recommendations": [ - "platformio.platformio-ide" - ], - "unwantedRecommendations": [ - "ms-vscode.cpptools-extension-pack" - ] -} diff --git a/bitlair_doorduino_door/src/main.cpp b/bitlair_doorduino_door/bitlair_doorduino_door.ino similarity index 94% rename from bitlair_doorduino_door/src/main.cpp rename to bitlair_doorduino_door/bitlair_doorduino_door.ino index d7a133b..1cab59d 100644 --- a/bitlair_doorduino_door/src/main.cpp +++ b/bitlair_doorduino_door/bitlair_doorduino_door.ino @@ -89,13 +89,13 @@ void setup() { state = STATE_OPEN; Serial.println("RECEIVED OPEN"); stepper.enable(); - stepper.startRotate(-900); + stepper.startRotate(-560); } if (digitalRead(DOOR_CLOSE) == HIGH && state == STATE_IDLE){ state = STATE_CLOSE; Serial.println("RECEIVED CLOSE"); stepper.enable(); - stepper.startRotate(900); + stepper.startRotate(560); } } diff --git a/bitlair_doorduino_door/include/README b/bitlair_doorduino_door/include/README deleted file mode 100644 index 45496b1..0000000 --- a/bitlair_doorduino_door/include/README +++ /dev/null @@ -1,39 +0,0 @@ - -This directory is intended for project header files. - -A header file is a file containing C declarations and macro definitions -to be shared between several project source files. You request the use of a -header file in your project source file (C, C++, etc) located in `src` folder -by including it, with the C preprocessing directive `#include'. - -```src/main.c - -#include "header.h" - -int main (void) -{ - ... -} -``` - -Including a header file produces the same results as copying the header file -into each source file that needs it. Such copying would be time-consuming -and error-prone. With a header file, the related declarations appear -in only one place. If they need to be changed, they can be changed in one -place, and programs that include the header file will automatically use the -new version when next recompiled. The header file eliminates the labor of -finding and changing all the copies as well as the risk that a failure to -find one copy will result in inconsistencies within a program. - -In C, the usual convention is to give header files names that end with `.h'. -It is most portable to use only letters, digits, dashes, and underscores in -header file names, and at most one dot. - -Read more about using header files in official GCC documentation: - -* Include Syntax -* Include Operation -* Once-Only Headers -* Computed Includes - -https://gcc.gnu.org/onlinedocs/cpp/Header-Files.html diff --git a/bitlair_doorduino_door/lib/README b/bitlair_doorduino_door/lib/README deleted file mode 100644 index 8c9c29c..0000000 --- a/bitlair_doorduino_door/lib/README +++ /dev/null @@ -1,46 +0,0 @@ - -This directory is intended for project specific (private) libraries. -PlatformIO will compile them to static libraries and link into executable file. - -The source code of each library should be placed in a an own separate directory -("lib/your_library_name/[here are source files]"). - -For example, see a structure of the following two libraries `Foo` and `Bar`: - -|--lib -| | -| |--Bar -| | |--docs -| | |--examples -| | |--src -| | |- Bar.c -| | |- Bar.h -| | |- library.json (optional, custom build options, etc) https://docs.platformio.org/page/librarymanager/config.html -| | -| |--Foo -| | |- Foo.c -| | |- Foo.h -| | -| |- README --> THIS FILE -| -|- platformio.ini -|--src - |- main.c - -and a contents of `src/main.c`: -``` -#include -#include - -int main (void) -{ - ... -} - -``` - -PlatformIO Library Dependency Finder will find automatically dependent -libraries scanning project source files. - -More information about PlatformIO Library Dependency Finder -- https://docs.platformio.org/page/librarymanager/ldf.html diff --git a/bitlair_doorduino_door/platformio.ini b/bitlair_doorduino_door/platformio.ini deleted file mode 100644 index 985f8a1..0000000 --- a/bitlair_doorduino_door/platformio.ini +++ /dev/null @@ -1,20 +0,0 @@ -; PlatformIO Project Configuration File -; -; Build options: build flags, source filter -; Upload options: custom upload port, speed and extra flags -; Library options: dependencies, extra library storages -; Advanced options: extra scripting -; -; Please visit documentation for the other options and examples -; https://docs.platformio.org/page/projectconf.html - -[env:prominiatmega328] -platform = atmelavr -board = pro16MHzatmega328 -framework = arduino - -lib_deps = - laurb9/StepperDriver@^1.4.1 - https://github.com/sosandroid/AMS_AS5048B.git - -monitor_speed = 115200 diff --git a/bitlair_doorduino_door/test/README b/bitlair_doorduino_door/test/README deleted file mode 100644 index e7d1588..0000000 --- a/bitlair_doorduino_door/test/README +++ /dev/null @@ -1,11 +0,0 @@ - -This directory is intended for PlatformIO Unit Testing and project tests. - -Unit Testing is a software testing method by which individual units of -source code, sets of one or more MCU program modules together with associated -control data, usage procedures, and operating procedures, are tested to -determine whether they are fit for use. Unit testing finds problems early -in the development cycle. - -More information about PlatformIO Unit Testing: -- https://docs.platformio.org/page/plus/unit-testing.html diff --git a/bitlair_doorduino_inner/.gitignore b/bitlair_doorduino_inner/.gitignore deleted file mode 100644 index 89cc49c..0000000 --- a/bitlair_doorduino_inner/.gitignore +++ /dev/null @@ -1,5 +0,0 @@ -.pio -.vscode/.browse.c_cpp.db* -.vscode/c_cpp_properties.json -.vscode/launch.json -.vscode/ipch diff --git a/bitlair_doorduino_inner/.vscode/extensions.json b/bitlair_doorduino_inner/.vscode/extensions.json deleted file mode 100644 index 080e70d..0000000 --- a/bitlair_doorduino_inner/.vscode/extensions.json +++ /dev/null @@ -1,10 +0,0 @@ -{ - // See http://go.microsoft.com/fwlink/?LinkId=827846 - // for the documentation about the extensions.json format - "recommendations": [ - "platformio.platformio-ide" - ], - "unwantedRecommendations": [ - "ms-vscode.cpptools-extension-pack" - ] -} diff --git a/bitlair_doorduino_inner/include/README b/bitlair_doorduino_inner/include/README deleted file mode 100644 index 45496b1..0000000 --- a/bitlair_doorduino_inner/include/README +++ /dev/null @@ -1,39 +0,0 @@ - -This directory is intended for project header files. - -A header file is a file containing C declarations and macro definitions -to be shared between several project source files. You request the use of a -header file in your project source file (C, C++, etc) located in `src` folder -by including it, with the C preprocessing directive `#include'. - -```src/main.c - -#include "header.h" - -int main (void) -{ - ... -} -``` - -Including a header file produces the same results as copying the header file -into each source file that needs it. Such copying would be time-consuming -and error-prone. With a header file, the related declarations appear -in only one place. If they need to be changed, they can be changed in one -place, and programs that include the header file will automatically use the -new version when next recompiled. The header file eliminates the labor of -finding and changing all the copies as well as the risk that a failure to -find one copy will result in inconsistencies within a program. - -In C, the usual convention is to give header files names that end with `.h'. -It is most portable to use only letters, digits, dashes, and underscores in -header file names, and at most one dot. - -Read more about using header files in official GCC documentation: - -* Include Syntax -* Include Operation -* Once-Only Headers -* Computed Includes - -https://gcc.gnu.org/onlinedocs/cpp/Header-Files.html diff --git a/bitlair_doorduino_inner/lib/README b/bitlair_doorduino_inner/lib/README deleted file mode 100644 index 8c9c29c..0000000 --- a/bitlair_doorduino_inner/lib/README +++ /dev/null @@ -1,46 +0,0 @@ - -This directory is intended for project specific (private) libraries. -PlatformIO will compile them to static libraries and link into executable file. - -The source code of each library should be placed in a an own separate directory -("lib/your_library_name/[here are source files]"). - -For example, see a structure of the following two libraries `Foo` and `Bar`: - -|--lib -| | -| |--Bar -| | |--docs -| | |--examples -| | |--src -| | |- Bar.c -| | |- Bar.h -| | |- library.json (optional, custom build options, etc) https://docs.platformio.org/page/librarymanager/config.html -| | -| |--Foo -| | |- Foo.c -| | |- Foo.h -| | -| |- README --> THIS FILE -| -|- platformio.ini -|--src - |- main.c - -and a contents of `src/main.c`: -``` -#include -#include - -int main (void) -{ - ... -} - -``` - -PlatformIO Library Dependency Finder will find automatically dependent -libraries scanning project source files. - -More information about PlatformIO Library Dependency Finder -- https://docs.platformio.org/page/librarymanager/ldf.html diff --git a/bitlair_doorduino_inner/platformio.ini b/bitlair_doorduino_inner/platformio.ini deleted file mode 100644 index e5d0646..0000000 --- a/bitlair_doorduino_inner/platformio.ini +++ /dev/null @@ -1,19 +0,0 @@ -; PlatformIO Project Configuration File -; -; Build options: build flags, source filter -; Upload options: custom upload port, speed and extra flags -; Library options: dependencies, extra library storages -; Advanced options: extra scripting -; -; Please visit documentation for the other options and examples -; https://docs.platformio.org/page/projectconf.html - -[env:nanoatmega328] -platform = atmelavr -board = nanoatmega328new -framework = arduino - -lib_deps = - laurb9/StepperDriver@^1.3.1 - -monitor_speed = 115200 diff --git a/bitlair_doorduino_inner/src/Entropy.cpp b/bitlair_doorduino_inner/src/Entropy.cpp deleted file mode 100644 index 7a83a4d..0000000 --- a/bitlair_doorduino_inner/src/Entropy.cpp +++ /dev/null @@ -1,344 +0,0 @@ -// Entropy - A entropy (random number) generator for the Arduino -// The latest version of this library will always be stored in the following -// google code repository: -// http://code.google.com/p/avr-hardware-random-number-generation/source/browse/#git%2FEntropy -// with more information available on the libraries wiki page -// http://code.google.com/p/avr-hardware-random-number-generation/wiki/WikiAVRentropy -// -// Copyright 2014 by Walter Anderson -// -// This file is part of Entropy, an Arduino library. -// Entropy is free software: you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// Entropy is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License for more details. -// -// You should have received a copy of the GNU General Public License -// along with Entropy. If not, see . - -#include -#include "Entropy.h" - -const uint8_t WDT_MAX_8INT=0xFF; -const uint16_t WDT_MAX_16INT=0xFFFF; -const uint32_t WDT_MAX_32INT=0xFFFFFFFF; -// Since the Due TRNG is so fast we don't need a circular buffer for it -#ifndef ARDUINO_SAM_DUE - const uint8_t gWDT_buffer_SIZE=32; - const uint8_t WDT_POOL_SIZE=8; - uint8_t gWDT_buffer[gWDT_buffer_SIZE]; - uint8_t gWDT_buffer_position; - uint8_t gWDT_loop_counter; - volatile uint8_t gWDT_pool_start; - volatile uint8_t gWDT_pool_end; - volatile uint8_t gWDT_pool_count; - volatile uint32_t gWDT_entropy_pool[WDT_POOL_SIZE]; -#endif - -// This function initializes the global variables needed to implement the circular entropy pool and -// the buffer that holds the raw Timer 1 values that are used to create the entropy pool. It then -// Initializes the Watch Dog Timer (WDT) to perform an interrupt every 2048 clock cycles, (about -// 16 ms) which is as fast as it can be set. -void EntropyClass::initialize(void) -{ -#ifndef ARDUINO_SAM_DUE - gWDT_buffer_position=0; - gWDT_pool_start = 0; - gWDT_pool_end = 0; - gWDT_pool_count = 0; -#endif -#if defined(__AVR__) - cli(); // Temporarily turn off interrupts, until WDT configured - MCUSR = 0; // Use the MCU status register to reset flags for WDR, BOR, EXTR, and POWR - _WD_CONTROL_REG |= (1<<_WD_CHANGE_BIT) | (1<TRNG_IDR = 0xFFFFFFFF; - TRNG->TRNG_CR = TRNG_CR_KEY(0x524e47) | TRNG_CR_ENABLE; -#elif defined(__arm__) && defined(TEENSYDUINO) - SIM_SCGC5 |= SIM_SCGC5_LPTIMER; - LPTMR0_CSR = 0b10000100; - LPTMR0_PSR = 0b00000101; // PCS=01 : 1 kHz clock - LPTMR0_CMR = 0x0006; // smaller number = faster random numbers... - LPTMR0_CSR = 0b01000101; - NVIC_ENABLE_IRQ(IRQ_LPTMR); -#endif -} - -// This function returns a uniformly distributed random integer in the range -// of [0,0xFFFFFFFF] as long as some entropy exists in the pool and a 0 -// otherwise. To ensure a proper random return the available() function -// should be called first to ensure that entropy exists. -// -// The pool is implemented as an 8 value circular buffer -uint32_t EntropyClass::random(void) -{ -#ifdef ARDUINO_SAM_DUE - while (! (TRNG->TRNG_ISR & TRNG_ISR_DATRDY)) - ; - retVal = TRNG->TRNG_ODATA; -#else - uint8_t waiting; - while (gWDT_pool_count < 1) - waiting += 1; - ATOMIC_BLOCK(ATOMIC_RESTORESTATE) - { - retVal = gWDT_entropy_pool[gWDT_pool_start]; - gWDT_pool_start = (gWDT_pool_start + 1) % WDT_POOL_SIZE; - --gWDT_pool_count; - } -#endif - return(retVal); -} - -// This function returns one byte of a single 32-bit entropy value, while preserving the remaining bytes to -// be returned upon successive calls to the method. This makes best use of the available entropy pool when -// only bytes size chunks of entropy are needed. Not available to public use since there is a method of using -// the default random method for the end-user to achieve the same results. This internal method is for providing -// that capability to the random method, shown below -uint8_t EntropyClass::random8(void) -{ - static uint8_t byte_position=0; - uint8_t retVal8; - - if (byte_position == 0) - share_entropy.int32 = random(); - retVal8 = share_entropy.int8[byte_position++]; - byte_position = byte_position % 4; - return(retVal8); -} - -// This function returns one word of a single 32-bit entropy value, while preserving the remaining word to -// be returned upon successive calls to the method. This makes best use of the available entropy pool when -// only word sized chunks of entropy are needed. Not available to public use since there is a method of using -// the default random method for the end-user to achieve the same results. This internal method is for providing -// that capability to the random method, shown below -uint16_t EntropyClass::random16(void) -{ - static uint8_t word_position=0; - uint16_t retVal16; - - if (word_position == 0) - share_entropy.int32 = random(); - retVal16 = share_entropy.int16[word_position++]; - word_position = word_position % 2; - return(retVal16); -} - -uint8_t EntropyClass::randomByte(void) -{ - return random8(); -} - -uint16_t EntropyClass::randomWord(void) -{ - return random16(); -} - -// This function returns a uniformly distributed integer in the range of -// of [0,max). The added complexity of this function is required to ensure -// a uniform distribution since the naive modulus max (% max) introduces -// bias for all values of max that are not powers of two. -// -// The loops below are needed, because there is a small and non-uniform chance -// That the division below will yield an answer = max, so we just get -// the next random value until answer < max. Which prevents the introduction -// of bias caused by the division process. This is why we can't use the -// simpler modulus operation which introduces significant bias for divisors -// that aren't a power of two -uint32_t EntropyClass::random(uint32_t max) -{ - uint32_t slice; - - if (max < 2) - retVal=0; - else - { - retVal = WDT_MAX_32INT; - if (max <= WDT_MAX_8INT) // If only byte values are needed, make best use of entropy - { // by diving the long into four bytes and using individually - slice = WDT_MAX_8INT / max; - while (retVal >= max) - retVal = random8() / slice; - } - else if (max <= WDT_MAX_16INT) // If only word values are need, make best use of entropy - { // by diving the long into two words and using individually - slice = WDT_MAX_16INT / max; - while (retVal >= max) - retVal = random16() / slice; - } - else - { - slice = WDT_MAX_32INT / max; - while (retVal >= max) - retVal = random() / slice; - } - } - return(retVal); -} - -// This function returns a uniformly distributed integer in the range of -// of [min,max). -uint32_t EntropyClass::random(uint32_t min, uint32_t max) -{ - uint32_t tmp_random, tmax; - - tmax = max - min; - if (tmax < 1) - retVal=min; - else - { - tmp_random = random(tmax); - retVal = min + tmp_random; - } - return(retVal); -} - -// This function returns a uniformly distributed single precision floating point -// in the range of [0.0,1.0) -float EntropyClass::randomf(void) -{ - float fRetVal; - - // Since c++ doesn't allow bit manipulations of floating point types, we are - // using integer type and arrange its bit pattern to follow the IEEE754 bit - // pattern for single precision floating point value in the range of 1.0 - 2.0 - uint32_t tmp_random = random(); - tmp_random = (tmp_random & 0x007FFFFF) | 0x3F800000; - // We then copy that binary representation from the temporary integer to the - // returned floating point value - memcpy((void *) &fRetVal, (void *) &tmp_random, sizeof(fRetVal)); - // Now translate the value back to its intended range by subtracting 1.0 - fRetVal = fRetVal - 1.0; - return (fRetVal); -} - -// This function returns a uniformly distributed single precision floating point -// in the range of [0.0, max) -float EntropyClass::randomf(float max) -{ - float fRetVal; - fRetVal = randomf() * max; - return(fRetVal); -} - -// This function returns a uniformly distributed single precision floating point -// in the range of [min, max) -float EntropyClass::randomf(float min,float max) -{ - float fRetVal; - float tmax; - tmax = max - min; - fRetVal = (randomf() * tmax) + min; - return(fRetVal); -} - -// This function implements the Marsaglia polar method of converting a uniformly -// distributed random numbers to a normaly distributed (bell curve) with the -// mean and standard deviation specified. This type of random number is useful -// for a variety of purposes, like Monte Carlo simulations. -float EntropyClass::rnorm(float mean, float stdDev) -{ - static float spare; - static float u1; - static float u2; - static float s; - static bool isSpareReady = false; - - if (isSpareReady) - { - isSpareReady = false; - return ((spare * stdDev) + mean); - } else { - do { - u1 = (randomf() * 2) - 1; - u2 = (randomf() * 2) - 1; - s = (u1 * u1) + (u2 * u2); - } while (s >= 1.0); - s = sqrt(-2.0 * log(s) / s); - spare = u2 * s; - isSpareReady = true; - return(mean + (stdDev * u1 * s)); - } -} - -// This function returns a unsigned char (8-bit) with the number of unsigned long values -// in the entropy pool -uint8_t EntropyClass::available(void) -{ -#ifdef ARDUINO_SAM_DUE - return(TRNG->TRNG_ISR & TRNG_ISR_DATRDY); -#else - return(gWDT_pool_count); -#endif -} - -// Circular buffer is not needed with the speed of the Arduino Due trng hardware generator -#ifndef ARDUINO_SAM_DUE -// This interrupt service routine is called every time the WDT interrupt is triggered. -// With the default configuration that is approximately once every 16ms, producing -// approximately two 32-bit integer values every second. -// -// The pool is implemented as an 8 value circular buffer -static void isr_hardware_neutral(uint8_t val) -{ - gWDT_buffer[gWDT_buffer_position] = val; - gWDT_buffer_position++; // every time the WDT interrupt is triggered - if (gWDT_buffer_position >= gWDT_buffer_SIZE) - { - gWDT_pool_end = (gWDT_pool_start + gWDT_pool_count) % WDT_POOL_SIZE; - // The following code is an implementation of Jenkin's one at a time hash - // This hash function has had preliminary testing to verify that it - // produces reasonably uniform random results when using WDT jitter - // on a variety of Arduino platforms - for(gWDT_loop_counter = 0; gWDT_loop_counter < gWDT_buffer_SIZE; ++gWDT_loop_counter) - { - gWDT_entropy_pool[gWDT_pool_end] += gWDT_buffer[gWDT_loop_counter]; - gWDT_entropy_pool[gWDT_pool_end] += (gWDT_entropy_pool[gWDT_pool_end] << 10); - gWDT_entropy_pool[gWDT_pool_end] ^= (gWDT_entropy_pool[gWDT_pool_end] >> 6); - } - gWDT_entropy_pool[gWDT_pool_end] += (gWDT_entropy_pool[gWDT_pool_end] << 3); - gWDT_entropy_pool[gWDT_pool_end] ^= (gWDT_entropy_pool[gWDT_pool_end] >> 11); - gWDT_entropy_pool[gWDT_pool_end] += (gWDT_entropy_pool[gWDT_pool_end] << 15); - gWDT_entropy_pool[gWDT_pool_end] = gWDT_entropy_pool[gWDT_pool_end]; - gWDT_buffer_position = 0; // Start collecting the next 32 bytes of Timer 1 counts - if (gWDT_pool_count == WDT_POOL_SIZE) // The entropy pool is full - gWDT_pool_start = (gWDT_pool_start + 1) % WDT_POOL_SIZE; - else // Add another unsigned long (32 bits) to the entropy pool - ++gWDT_pool_count; - } -} -#endif - -#if defined( __AVR_ATtiny25__ ) || defined( __AVR_ATtiny45__ ) || defined( __AVR_ATtiny85__ ) -ISR(WDT_vect) -{ - isr_hardware_neutral(TCNT0); -} - -#elif defined(__AVR__) -ISR(WDT_vect) -{ - isr_hardware_neutral(TCNT1L); // Record the Timer 1 low byte (only one needed) -} - -#elif defined(__arm__) && defined(TEENSYDUINO) -void lptmr_isr(void) -{ - LPTMR0_CSR = 0b10000100; - LPTMR0_CSR = 0b01000101; - isr_hardware_neutral(SYST_CVR); -} -#endif - -// The library implements a single global instance. There is no need, nor will the library -// work properly if multiple instances are created. -EntropyClass Entropy; diff --git a/bitlair_doorduino_inner/src/Entropy.h b/bitlair_doorduino_inner/src/Entropy.h deleted file mode 100644 index 0d7d7a6..0000000 --- a/bitlair_doorduino_inner/src/Entropy.h +++ /dev/null @@ -1,73 +0,0 @@ -// Entropy - A entropy (random number) generator for the Arduino -// -// Copyright 2014 by Walter Anderson -// -// This file is part of Entropy, an Arduino library. -// Entropy is free software: you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// Entropy is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License for more details. -// -// You should have received a copy of the GNU General Public License -// along with Entropy. If not, see . - -#ifndef Entropy_h -#define Entropy_h - -#include - -// Separate the ARM Due headers we use -#ifdef ARDUINO_SAM_DUE -#include -#include -#endif - -// Teensy required headers -#ifdef TEENSYDUINO -#include -#endif - -// Separate AVR headers from ARM headers -#ifdef __AVR__ -#include -#include -#include -#endif - -const uint32_t WDT_RETURN_BYTE=256; -const uint32_t WDT_RETURN_WORD=65536; - -union ENTROPY_LONG_WORD -{ - uint32_t int32; - uint16_t int16[2]; - uint8_t int8[4]; -}; - -class EntropyClass -{ -public: - void initialize(void); - uint32_t random(void); - uint32_t random(uint32_t max); - uint32_t random(uint32_t min, uint32_t max); - uint8_t randomByte(void); - uint16_t randomWord(void); - float randomf(void); - float randomf(float max); - float randomf(float min, float max); - float rnorm(float mean, float stdDev); - uint8_t available(void); - private: - ENTROPY_LONG_WORD share_entropy; - uint32_t retVal; - uint8_t random8(void); - uint16_t random16(void); -}; -extern EntropyClass Entropy; -#endif diff --git a/bitlair_doorduino_inner/src/OneWire.cpp b/bitlair_doorduino_inner/src/OneWire.cpp deleted file mode 100644 index 6d55de0..0000000 --- a/bitlair_doorduino_inner/src/OneWire.cpp +++ /dev/null @@ -1,563 +0,0 @@ -/* -Copyright (c) 2007, Jim Studt (original old version - many contributors since) - -The latest version of this library may be found at: - http://www.pjrc.com/teensy/td_libs_OneWire.html - -OneWire has been maintained by Paul Stoffregen (paul@pjrc.com) since -January 2010. At the time, it was in need of many bug fixes, but had -been abandoned the original author (Jim Studt). None of the known -contributors were interested in maintaining OneWire. Paul typically -works on OneWire every 6 to 12 months. Patches usually wait that -long. If anyone is interested in more actively maintaining OneWire, -please contact Paul. - -Version 2.3: - Unknonw chip fallback mode, Roger Clark - Teensy-LC compatibility, Paul Stoffregen - Search bug fix, Love Nystrom - -Version 2.2: - Teensy 3.0 compatibility, Paul Stoffregen, paul@pjrc.com - Arduino Due compatibility, http://arduino.cc/forum/index.php?topic=141030 - Fix DS18B20 example negative temperature - Fix DS18B20 example's low res modes, Ken Butcher - Improve reset timing, Mark Tillotson - Add const qualifiers, Bertrik Sikken - Add initial value input to crc16, Bertrik Sikken - Add target_search() function, Scott Roberts - -Version 2.1: - Arduino 1.0 compatibility, Paul Stoffregen - Improve temperature example, Paul Stoffregen - DS250x_PROM example, Guillermo Lovato - PIC32 (chipKit) compatibility, Jason Dangel, dangel.jason AT gmail.com - Improvements from Glenn Trewitt: - - crc16() now works - - check_crc16() does all of calculation/checking work. - - Added read_bytes() and write_bytes(), to reduce tedious loops. - - Added ds2408 example. - Delete very old, out-of-date readme file (info is here) - -Version 2.0: Modifications by Paul Stoffregen, January 2010: -http://www.pjrc.com/teensy/td_libs_OneWire.html - Search fix from Robin James - http://www.arduino.cc/cgi-bin/yabb2/YaBB.pl?num=1238032295/27#27 - Use direct optimized I/O in all cases - Disable interrupts during timing critical sections - (this solves many random communication errors) - Disable interrupts during read-modify-write I/O - Reduce RAM consumption by eliminating unnecessary - variables and trimming many to 8 bits - Optimize both crc8 - table version moved to flash - -Modified to work with larger numbers of devices - avoids loop. -Tested in Arduino 11 alpha with 12 sensors. -26 Sept 2008 -- Robin James -http://www.arduino.cc/cgi-bin/yabb2/YaBB.pl?num=1238032295/27#27 - -Updated to work with arduino-0008 and to include skip() as of -2007/07/06. --RJL20 - -Modified to calculate the 8-bit CRC directly, avoiding the need for -the 256-byte lookup table to be loaded in RAM. Tested in arduino-0010 --- Tom Pollard, Jan 23, 2008 - -Jim Studt's original library was modified by Josh Larios. - -Tom Pollard, pollard@alum.mit.edu, contributed around May 20, 2008 - -Permission is hereby granted, free of charge, to any person obtaining -a copy of this software and associated documentation files (the -"Software"), to deal in the Software without restriction, including -without limitation the rights to use, copy, modify, merge, publish, -distribute, sublicense, and/or sell copies of the Software, and to -permit persons to whom the Software is furnished to do so, subject to -the following conditions: - -The above copyright notice and this permission notice shall be -included in all copies or substantial portions of the Software. - -THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, -EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF -MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND -NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE -LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION -OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION -WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. - -Much of the code was inspired by Derek Yerger's code, though I don't -think much of that remains. In any event that was.. - (copyleft) 2006 by Derek Yerger - Free to distribute freely. - -The CRC code was excerpted and inspired by the Dallas Semiconductor -sample code bearing this copyright. -//--------------------------------------------------------------------------- -// Copyright (C) 2000 Dallas Semiconductor Corporation, All Rights Reserved. -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the "Software"), -// to deal in the Software without restriction, including without limitation -// the rights to use, copy, modify, merge, publish, distribute, sublicense, -// and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included -// in all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS -// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF -// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. -// IN NO EVENT SHALL DALLAS SEMICONDUCTOR BE LIABLE FOR ANY CLAIM, DAMAGES -// OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, -// ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR -// OTHER DEALINGS IN THE SOFTWARE. -// -// Except as contained in this notice, the name of Dallas Semiconductor -// shall not be used except as stated in the Dallas Semiconductor -// Branding Policy. -//-------------------------------------------------------------------------- -*/ - -#include "OneWire.h" - - -OneWire::OneWire(uint8_t pin) -{ - pinMode(pin, INPUT); - bitmask = PIN_TO_BITMASK(pin); - baseReg = PIN_TO_BASEREG(pin); -#if ONEWIRE_SEARCH - reset_search(); -#endif -} - - -// Perform the onewire reset function. We will wait up to 250uS for -// the bus to come high, if it doesn't then it is broken or shorted -// and we return a 0; -// -// Returns 1 if a device asserted a presence pulse, 0 otherwise. -// -uint8_t OneWire::reset(void) -{ - IO_REG_TYPE mask = bitmask; - volatile IO_REG_TYPE *reg IO_REG_ASM = baseReg; - uint8_t r; - uint8_t retries = 125; - - noInterrupts(); - DIRECT_MODE_INPUT(reg, mask); - interrupts(); - // wait until the wire is high... just in case - do { - if (--retries == 0) return 0; - delayMicroseconds(2); - } while ( !DIRECT_READ(reg, mask)); - - noInterrupts(); - DIRECT_WRITE_LOW(reg, mask); - DIRECT_MODE_OUTPUT(reg, mask); // drive output low - interrupts(); - delayMicroseconds(480); - noInterrupts(); - DIRECT_MODE_INPUT(reg, mask); // allow it to float - delayMicroseconds(70); - r = !DIRECT_READ(reg, mask); - interrupts(); - delayMicroseconds(410); - return r; -} - -// -// Write a bit. Port and bit is used to cut lookup time and provide -// more certain timing. -// -void OneWire::write_bit(uint8_t v) -{ - IO_REG_TYPE mask=bitmask; - volatile IO_REG_TYPE *reg IO_REG_ASM = baseReg; - - if (v & 1) { - noInterrupts(); - DIRECT_WRITE_LOW(reg, mask); - DIRECT_MODE_OUTPUT(reg, mask); // drive output low - delayMicroseconds(10); - DIRECT_WRITE_HIGH(reg, mask); // drive output high - interrupts(); - delayMicroseconds(55); - } else { - noInterrupts(); - DIRECT_WRITE_LOW(reg, mask); - DIRECT_MODE_OUTPUT(reg, mask); // drive output low - delayMicroseconds(65); - DIRECT_WRITE_HIGH(reg, mask); // drive output high - interrupts(); - delayMicroseconds(5); - } -} - -// -// Read a bit. Port and bit is used to cut lookup time and provide -// more certain timing. -// -uint8_t OneWire::read_bit(void) -{ - IO_REG_TYPE mask=bitmask; - volatile IO_REG_TYPE *reg IO_REG_ASM = baseReg; - uint8_t r; - - noInterrupts(); - DIRECT_MODE_OUTPUT(reg, mask); - DIRECT_WRITE_LOW(reg, mask); - delayMicroseconds(3); - DIRECT_MODE_INPUT(reg, mask); // let pin float, pull up will raise - delayMicroseconds(10); - r = DIRECT_READ(reg, mask); - interrupts(); - delayMicroseconds(53); - return r; -} - -// -// Write a byte. The writing code uses the active drivers to raise the -// pin high, if you need power after the write (e.g. DS18S20 in -// parasite power mode) then set 'power' to 1, otherwise the pin will -// go tri-state at the end of the write to avoid heating in a short or -// other mishap. -// -void OneWire::write(uint8_t v, uint8_t power /* = 0 */) { - uint8_t bitMask; - - for (bitMask = 0x01; bitMask; bitMask <<= 1) { - OneWire::write_bit( (bitMask & v)?1:0); - } - if ( !power) { - noInterrupts(); - DIRECT_MODE_INPUT(baseReg, bitmask); - DIRECT_WRITE_LOW(baseReg, bitmask); - interrupts(); - } -} - -void OneWire::write_bytes(const uint8_t *buf, uint16_t count, bool power /* = 0 */) { - for (uint16_t i = 0 ; i < count ; i++) - write(buf[i]); - if (!power) { - noInterrupts(); - DIRECT_MODE_INPUT(baseReg, bitmask); - DIRECT_WRITE_LOW(baseReg, bitmask); - interrupts(); - } -} - -// -// Read a byte -// -uint8_t OneWire::read() { - uint8_t bitMask; - uint8_t r = 0; - - for (bitMask = 0x01; bitMask; bitMask <<= 1) { - if ( OneWire::read_bit()) r |= bitMask; - } - return r; -} - -void OneWire::read_bytes(uint8_t *buf, uint16_t count) { - for (uint16_t i = 0 ; i < count ; i++) - buf[i] = read(); -} - -// -// Do a ROM select -// -void OneWire::select(const uint8_t rom[8]) -{ - uint8_t i; - - write(0x55); // Choose ROM - - for (i = 0; i < 8; i++) write(rom[i]); -} - -// -// Do a ROM skip -// -void OneWire::skip() -{ - write(0xCC); // Skip ROM -} - -void OneWire::depower() -{ - noInterrupts(); - DIRECT_MODE_INPUT(baseReg, bitmask); - interrupts(); -} - -#if ONEWIRE_SEARCH - -// -// You need to use this function to start a search again from the beginning. -// You do not need to do it for the first search, though you could. -// -void OneWire::reset_search() -{ - // reset the search state - LastDiscrepancy = 0; - LastDeviceFlag = FALSE; - LastFamilyDiscrepancy = 0; - for(int i = 7; ; i--) { - ROM_NO[i] = 0; - if ( i == 0) break; - } -} - -// Setup the search to find the device type 'family_code' on the next call -// to search(*newAddr) if it is present. -// -void OneWire::target_search(uint8_t family_code) -{ - // set the search state to find SearchFamily type devices - ROM_NO[0] = family_code; - for (uint8_t i = 1; i < 8; i++) - ROM_NO[i] = 0; - LastDiscrepancy = 64; - LastFamilyDiscrepancy = 0; - LastDeviceFlag = FALSE; -} - -// -// Perform a search. If this function returns a '1' then it has -// enumerated the next device and you may retrieve the ROM from the -// OneWire::address variable. If there are no devices, no further -// devices, or something horrible happens in the middle of the -// enumeration then a 0 is returned. If a new device is found then -// its address is copied to newAddr. Use OneWire::reset_search() to -// start over. -// -// --- Replaced by the one from the Dallas Semiconductor web site --- -//-------------------------------------------------------------------------- -// Perform the 1-Wire Search Algorithm on the 1-Wire bus using the existing -// search state. -// Return TRUE : device found, ROM number in ROM_NO buffer -// FALSE : device not found, end of search -// -uint8_t OneWire::search(uint8_t *newAddr) -{ - uint8_t id_bit_number; - uint8_t last_zero, rom_byte_number, search_result; - uint8_t id_bit, cmp_id_bit; - - unsigned char rom_byte_mask, search_direction; - - // initialize for search - id_bit_number = 1; - last_zero = 0; - rom_byte_number = 0; - rom_byte_mask = 1; - search_result = 0; - - // if the last call was not the last one - if (!LastDeviceFlag) - { - // 1-Wire reset - if (!reset()) - { - // reset the search - LastDiscrepancy = 0; - LastDeviceFlag = FALSE; - LastFamilyDiscrepancy = 0; - return FALSE; - } - - // issue the search command - write(0xF0); - - // loop to do the search - do - { - // read a bit and its complement - id_bit = read_bit(); - cmp_id_bit = read_bit(); - - // check for no devices on 1-wire - if ((id_bit == 1) && (cmp_id_bit == 1)) - break; - else - { - // all devices coupled have 0 or 1 - if (id_bit != cmp_id_bit) - search_direction = id_bit; // bit write value for search - else - { - // if this discrepancy if before the Last Discrepancy - // on a previous next then pick the same as last time - if (id_bit_number < LastDiscrepancy) - search_direction = ((ROM_NO[rom_byte_number] & rom_byte_mask) > 0); - else - // if equal to last pick 1, if not then pick 0 - search_direction = (id_bit_number == LastDiscrepancy); - - // if 0 was picked then record its position in LastZero - if (search_direction == 0) - { - last_zero = id_bit_number; - - // check for Last discrepancy in family - if (last_zero < 9) - LastFamilyDiscrepancy = last_zero; - } - } - - // set or clear the bit in the ROM byte rom_byte_number - // with mask rom_byte_mask - if (search_direction == 1) - ROM_NO[rom_byte_number] |= rom_byte_mask; - else - ROM_NO[rom_byte_number] &= ~rom_byte_mask; - - // serial number search direction write bit - write_bit(search_direction); - - // increment the byte counter id_bit_number - // and shift the mask rom_byte_mask - id_bit_number++; - rom_byte_mask <<= 1; - - // if the mask is 0 then go to new SerialNum byte rom_byte_number and reset mask - if (rom_byte_mask == 0) - { - rom_byte_number++; - rom_byte_mask = 1; - } - } - } - while(rom_byte_number < 8); // loop until through all ROM bytes 0-7 - - // if the search was successful then - if (!(id_bit_number < 65)) - { - // search successful so set LastDiscrepancy,LastDeviceFlag,search_result - LastDiscrepancy = last_zero; - - // check for last device - if (LastDiscrepancy == 0) - LastDeviceFlag = TRUE; - - search_result = TRUE; - } - } - - // if no device found then reset counters so next 'search' will be like a first - if (!search_result || !ROM_NO[0]) - { - LastDiscrepancy = 0; - LastDeviceFlag = FALSE; - LastFamilyDiscrepancy = 0; - search_result = FALSE; - } else { - for (int i = 0; i < 8; i++) newAddr[i] = ROM_NO[i]; - } - return search_result; - } - -#endif - -#if ONEWIRE_CRC -// The 1-Wire CRC scheme is described in Maxim Application Note 27: -// "Understanding and Using Cyclic Redundancy Checks with Maxim iButton Products" -// - -#if ONEWIRE_CRC8_TABLE -// This table comes from Dallas sample code where it is freely reusable, -// though Copyright (C) 2000 Dallas Semiconductor Corporation -static const uint8_t PROGMEM dscrc_table[] = { - 0, 94,188,226, 97, 63,221,131,194,156,126, 32,163,253, 31, 65, - 157,195, 33,127,252,162, 64, 30, 95, 1,227,189, 62, 96,130,220, - 35,125,159,193, 66, 28,254,160,225,191, 93, 3,128,222, 60, 98, - 190,224, 2, 92,223,129, 99, 61,124, 34,192,158, 29, 67,161,255, - 70, 24,250,164, 39,121,155,197,132,218, 56,102,229,187, 89, 7, - 219,133,103, 57,186,228, 6, 88, 25, 71,165,251,120, 38,196,154, - 101, 59,217,135, 4, 90,184,230,167,249, 27, 69,198,152,122, 36, - 248,166, 68, 26,153,199, 37,123, 58,100,134,216, 91, 5,231,185, - 140,210, 48,110,237,179, 81, 15, 78, 16,242,172, 47,113,147,205, - 17, 79,173,243,112, 46,204,146,211,141,111, 49,178,236, 14, 80, - 175,241, 19, 77,206,144,114, 44,109, 51,209,143, 12, 82,176,238, - 50,108,142,208, 83, 13,239,177,240,174, 76, 18,145,207, 45,115, - 202,148,118, 40,171,245, 23, 73, 8, 86,180,234,105, 55,213,139, - 87, 9,235,181, 54,104,138,212,149,203, 41,119,244,170, 72, 22, - 233,183, 85, 11,136,214, 52,106, 43,117,151,201, 74, 20,246,168, - 116, 42,200,150, 21, 75,169,247,182,232, 10, 84,215,137,107, 53}; - -// -// Compute a Dallas Semiconductor 8 bit CRC. These show up in the ROM -// and the registers. (note: this might better be done without to -// table, it would probably be smaller and certainly fast enough -// compared to all those delayMicrosecond() calls. But I got -// confused, so I use this table from the examples.) -// -uint8_t OneWire::crc8(const uint8_t *addr, uint8_t len) -{ - uint8_t crc = 0; - - while (len--) { - crc = pgm_read_byte(dscrc_table + (crc ^ *addr++)); - } - return crc; -} -#else -// -// Compute a Dallas Semiconductor 8 bit CRC directly. -// this is much slower, but much smaller, than the lookup table. -// -uint8_t OneWire::crc8(const uint8_t *addr, uint8_t len) -{ - uint8_t crc = 0; - - while (len--) { - uint8_t inbyte = *addr++; - for (uint8_t i = 8; i; i--) { - uint8_t mix = (crc ^ inbyte) & 0x01; - crc >>= 1; - if (mix) crc ^= 0x8C; - inbyte >>= 1; - } - } - return crc; -} -#endif - -#if ONEWIRE_CRC16 -bool OneWire::check_crc16(const uint8_t* input, uint16_t len, const uint8_t* inverted_crc, uint16_t crc) -{ - crc = ~crc16(input, len, crc); - return (crc & 0xFF) == inverted_crc[0] && (crc >> 8) == inverted_crc[1]; -} - -uint16_t OneWire::crc16(const uint8_t* input, uint16_t len, uint16_t crc) -{ - static const uint8_t oddparity[16] = - { 0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0 }; - - for (uint16_t i = 0 ; i < len ; i++) { - // Even though we're just copying a byte from the input, - // we'll be doing 16-bit computation with it. - uint16_t cdata = input[i]; - cdata = (cdata ^ crc) & 0xff; - crc >>= 8; - - if (oddparity[cdata & 0x0F] ^ oddparity[cdata >> 4]) - crc ^= 0xC001; - - cdata <<= 6; - crc ^= cdata; - cdata <<= 1; - crc ^= cdata; - } - return crc; -} -#endif - -#endif diff --git a/bitlair_doorduino_inner/src/OneWire.h b/bitlair_doorduino_inner/src/OneWire.h deleted file mode 100644 index be62737..0000000 --- a/bitlair_doorduino_inner/src/OneWire.h +++ /dev/null @@ -1,250 +0,0 @@ -#ifndef OneWire_h -#define OneWire_h - -#include - -#if ARDUINO >= 100 -#include "Arduino.h" // for delayMicroseconds, digitalPinToBitMask, etc -#else -#include "WProgram.h" // for delayMicroseconds -#include "pins_arduino.h" // for digitalPinToBitMask, etc -#endif - -// You can exclude certain features from OneWire. In theory, this -// might save some space. In practice, the compiler automatically -// removes unused code (technically, the linker, using -fdata-sections -// and -ffunction-sections when compiling, and Wl,--gc-sections -// when linking), so most of these will not result in any code size -// reduction. Well, unless you try to use the missing features -// and redesign your program to not need them! ONEWIRE_CRC8_TABLE -// is the exception, because it selects a fast but large algorithm -// or a small but slow algorithm. - -// you can exclude onewire_search by defining that to 0 -#ifndef ONEWIRE_SEARCH -#define ONEWIRE_SEARCH 1 -#endif - -// You can exclude CRC checks altogether by defining this to 0 -#ifndef ONEWIRE_CRC -#define ONEWIRE_CRC 1 -#endif - -// Select the table-lookup method of computing the 8-bit CRC -// by setting this to 1. The lookup table enlarges code size by -// about 250 bytes. It does NOT consume RAM (but did in very -// old versions of OneWire). If you disable this, a slower -// but very compact algorithm is used. -#ifndef ONEWIRE_CRC8_TABLE -#define ONEWIRE_CRC8_TABLE 1 -#endif - -// You can allow 16-bit CRC checks by defining this to 1 -// (Note that ONEWIRE_CRC must also be 1.) -#ifndef ONEWIRE_CRC16 -#define ONEWIRE_CRC16 1 -#endif - -#define FALSE 0 -#define TRUE 1 - -// Platform specific I/O definitions - -#if defined(__AVR__) -#define PIN_TO_BASEREG(pin) (portInputRegister(digitalPinToPort(pin))) -#define PIN_TO_BITMASK(pin) (digitalPinToBitMask(pin)) -#define IO_REG_TYPE uint8_t -#define IO_REG_ASM asm("r30") -#define DIRECT_READ(base, mask) (((*(base)) & (mask)) ? 1 : 0) -#define DIRECT_MODE_INPUT(base, mask) ((*((base)+1)) &= ~(mask)) -#define DIRECT_MODE_OUTPUT(base, mask) ((*((base)+1)) |= (mask)) -#define DIRECT_WRITE_LOW(base, mask) ((*((base)+2)) &= ~(mask)) -#define DIRECT_WRITE_HIGH(base, mask) ((*((base)+2)) |= (mask)) - -#elif defined(__MK20DX128__) || defined(__MK20DX256__) -#define PIN_TO_BASEREG(pin) (portOutputRegister(pin)) -#define PIN_TO_BITMASK(pin) (1) -#define IO_REG_TYPE uint8_t -#define IO_REG_ASM -#define DIRECT_READ(base, mask) (*((base)+512)) -#define DIRECT_MODE_INPUT(base, mask) (*((base)+640) = 0) -#define DIRECT_MODE_OUTPUT(base, mask) (*((base)+640) = 1) -#define DIRECT_WRITE_LOW(base, mask) (*((base)+256) = 1) -#define DIRECT_WRITE_HIGH(base, mask) (*((base)+128) = 1) - -#elif defined(__MKL26Z64__) -#define PIN_TO_BASEREG(pin) (portOutputRegister(pin)) -#define PIN_TO_BITMASK(pin) (digitalPinToBitMask(pin)) -#define IO_REG_TYPE uint8_t -#define IO_REG_ASM -#define DIRECT_READ(base, mask) ((*((base)+16) & (mask)) ? 1 : 0) -#define DIRECT_MODE_INPUT(base, mask) (*((base)+20) &= ~(mask)) -#define DIRECT_MODE_OUTPUT(base, mask) (*((base)+20) |= (mask)) -#define DIRECT_WRITE_LOW(base, mask) (*((base)+8) = (mask)) -#define DIRECT_WRITE_HIGH(base, mask) (*((base)+4) = (mask)) - -#elif defined(__SAM3X8E__) -// Arduino 1.5.1 may have a bug in delayMicroseconds() on Arduino Due. -// http://arduino.cc/forum/index.php/topic,141030.msg1076268.html#msg1076268 -// If you have trouble with OneWire on Arduino Due, please check the -// status of delayMicroseconds() before reporting a bug in OneWire! -#define PIN_TO_BASEREG(pin) (&(digitalPinToPort(pin)->PIO_PER)) -#define PIN_TO_BITMASK(pin) (digitalPinToBitMask(pin)) -#define IO_REG_TYPE uint32_t -#define IO_REG_ASM -#define DIRECT_READ(base, mask) (((*((base)+15)) & (mask)) ? 1 : 0) -#define DIRECT_MODE_INPUT(base, mask) ((*((base)+5)) = (mask)) -#define DIRECT_MODE_OUTPUT(base, mask) ((*((base)+4)) = (mask)) -#define DIRECT_WRITE_LOW(base, mask) ((*((base)+13)) = (mask)) -#define DIRECT_WRITE_HIGH(base, mask) ((*((base)+12)) = (mask)) -#ifndef PROGMEM -#define PROGMEM -#endif -#ifndef pgm_read_byte -#define pgm_read_byte(addr) (*(const uint8_t *)(addr)) -#endif - -#elif defined(__PIC32MX__) -#define PIN_TO_BASEREG(pin) (portModeRegister(digitalPinToPort(pin))) -#define PIN_TO_BITMASK(pin) (digitalPinToBitMask(pin)) -#define IO_REG_TYPE uint32_t -#define IO_REG_ASM -#define DIRECT_READ(base, mask) (((*(base+4)) & (mask)) ? 1 : 0) //PORTX + 0x10 -#define DIRECT_MODE_INPUT(base, mask) ((*(base+2)) = (mask)) //TRISXSET + 0x08 -#define DIRECT_MODE_OUTPUT(base, mask) ((*(base+1)) = (mask)) //TRISXCLR + 0x04 -#define DIRECT_WRITE_LOW(base, mask) ((*(base+8+1)) = (mask)) //LATXCLR + 0x24 -#define DIRECT_WRITE_HIGH(base, mask) ((*(base+8+2)) = (mask)) //LATXSET + 0x28 - -#else -#define PIN_TO_BASEREG(pin) (0) -#define PIN_TO_BITMASK(pin) (pin) -#define IO_REG_TYPE unsigned int -#define IO_REG_ASM -#define DIRECT_READ(base, pin) digitalRead(pin) -#define DIRECT_WRITE_LOW(base, pin) digitalWrite(pin, LOW) -#define DIRECT_WRITE_HIGH(base, pin) digitalWrite(pin, HIGH) -#define DIRECT_MODE_INPUT(base, pin) pinMode(pin,INPUT) -#define DIRECT_MODE_OUTPUT(base, pin) pinMode(pin,OUTPUT) -#warning "OneWire. Fallback mode. Using API calls for pinMode,digitalRead and digitalWrite. Operation of this library is not guaranteed on this architecture." - -#endif - - -class OneWire -{ - private: - IO_REG_TYPE bitmask; - volatile IO_REG_TYPE *baseReg; - -#if ONEWIRE_SEARCH - // global search state - unsigned char ROM_NO[8]; - uint8_t LastDiscrepancy; - uint8_t LastFamilyDiscrepancy; - uint8_t LastDeviceFlag; -#endif - - public: - OneWire( uint8_t pin); - - // Perform a 1-Wire reset cycle. Returns 1 if a device responds - // with a presence pulse. Returns 0 if there is no device or the - // bus is shorted or otherwise held low for more than 250uS - uint8_t reset(void); - - // Issue a 1-Wire rom select command, you do the reset first. - void select(const uint8_t rom[8]); - - // Issue a 1-Wire rom skip command, to address all on bus. - void skip(void); - - // Write a byte. If 'power' is one then the wire is held high at - // the end for parasitically powered devices. You are responsible - // for eventually depowering it by calling depower() or doing - // another read or write. - void write(uint8_t v, uint8_t power = 0); - - void write_bytes(const uint8_t *buf, uint16_t count, bool power = 0); - - // Read a byte. - uint8_t read(void); - - void read_bytes(uint8_t *buf, uint16_t count); - - // Write a bit. The bus is always left powered at the end, see - // note in write() about that. - void write_bit(uint8_t v); - - // Read a bit. - uint8_t read_bit(void); - - // Stop forcing power onto the bus. You only need to do this if - // you used the 'power' flag to write() or used a write_bit() call - // and aren't about to do another read or write. You would rather - // not leave this powered if you don't have to, just in case - // someone shorts your bus. - void depower(void); - -#if ONEWIRE_SEARCH - // Clear the search state so that if will start from the beginning again. - void reset_search(); - - // Setup the search to find the device type 'family_code' on the next call - // to search(*newAddr) if it is present. - void target_search(uint8_t family_code); - - // Look for the next device. Returns 1 if a new address has been - // returned. A zero might mean that the bus is shorted, there are - // no devices, or you have already retrieved all of them. It - // might be a good idea to check the CRC to make sure you didn't - // get garbage. The order is deterministic. You will always get - // the same devices in the same order. - uint8_t search(uint8_t *newAddr); -#endif - -#if ONEWIRE_CRC - // Compute a Dallas Semiconductor 8 bit CRC, these are used in the - // ROM and scratchpad registers. - static uint8_t crc8(const uint8_t *addr, uint8_t len); - -#if ONEWIRE_CRC16 - // Compute the 1-Wire CRC16 and compare it against the received CRC. - // Example usage (reading a DS2408): - // // Put everything in a buffer so we can compute the CRC easily. - // uint8_t buf[13]; - // buf[0] = 0xF0; // Read PIO Registers - // buf[1] = 0x88; // LSB address - // buf[2] = 0x00; // MSB address - // WriteBytes(net, buf, 3); // Write 3 cmd bytes - // ReadBytes(net, buf+3, 10); // Read 6 data bytes, 2 0xFF, 2 CRC16 - // if (!CheckCRC16(buf, 11, &buf[11])) { - // // Handle error. - // } - // - // @param input - Array of bytes to checksum. - // @param len - How many bytes to use. - // @param inverted_crc - The two CRC16 bytes in the received data. - // This should just point into the received data, - // *not* at a 16-bit integer. - // @param crc - The crc starting value (optional) - // @return True, iff the CRC matches. - static bool check_crc16(const uint8_t* input, uint16_t len, const uint8_t* inverted_crc, uint16_t crc = 0); - - // Compute a Dallas Semiconductor 16 bit CRC. This is required to check - // the integrity of data received from many 1-Wire devices. Note that the - // CRC computed here is *not* what you'll get from the 1-Wire network, - // for two reasons: - // 1) The CRC is transmitted bitwise inverted. - // 2) Depending on the endian-ness of your processor, the binary - // representation of the two-byte return value may have a different - // byte order than the two bytes you get from 1-Wire. - // @param input - Array of bytes to checksum. - // @param len - How many bytes to use. - // @param crc - The crc starting value (optional) - // @return The CRC16, as defined by Dallas Semiconductor. - static uint16_t crc16(const uint8_t* input, uint16_t len, uint16_t crc = 0); -#endif -#endif -}; - -#endif diff --git a/bitlair_doorduino_inner/src/ds1961.cpp b/bitlair_doorduino_inner/src/ds1961.cpp deleted file mode 100644 index 37f521e..0000000 --- a/bitlair_doorduino_inner/src/ds1961.cpp +++ /dev/null @@ -1,325 +0,0 @@ -#include -#include -#include - -#include "OneWire.h" -#include "ds1961.h" - -// commands used in the DS1961 standard -#define CMD_WRITE_SCRATCHPAD 0x0F -#define CMD_COMPUTE_NEXT_SECRET 0x33 -#define CMD_COPY_SCRATCHPAD 0x55 -#define CMD_LOAD_FIRST_SECRET 0x5A -#define CMD_REFRESH_SCRATCHPAD 0xA3 -#define CMD_READ_AUTH_PAGE 0xA5 -#define CMD_READ_SCRATCHPAD 0xAA -#define CMD_READ_MEMORY 0xF0 - -// memory ranges -#define MEM_DATA_PAGE_0 0x00 -#define MEM_DATA_PAGE_1 0x20 -#define MEM_DATA_PAGE_2 0x40 -#define MEM_DATA_PAGE_3 0x60 -#define MEM_SECRET 0x80 -#define MEM_IDENTITY 0x90 - -// timing (ms) -#define T_CSHA 2 // actually 1.5 -#define T_PROG 10 - - -DS1961::DS1961(OneWire *oneWire) -{ - ow = oneWire; -} - -static bool ResetAndSelect(OneWire *ow, const uint8_t id[8]) -{ - if (!ow->reset()) { - return false; - } - ow->select((uint8_t *) id); - - return true; -} - -static bool WriteScratchPad(OneWire *ow, const uint8_t id[8], uint16_t addr, const uint8_t data[8]) -{ - uint8_t buf[11]; - uint8_t crc[2]; - int len = 0; - - // reset and select - if (!ResetAndSelect(ow, id)) { - return false; - } - - // perform write scratchpad command - buf[len++] = CMD_WRITE_SCRATCHPAD; - buf[len++] = (addr >> 0) & 0xFF; // 2 byte target address - buf[len++] = (addr >> 8) & 0xFF; // 2 byte target address - memcpy(buf + len, data, 8); - len += 8; - ow->write_bytes(buf, len); - ow->read_bytes(crc, 2); - - return ow->check_crc16(buf, len, crc); -} - -static bool RefreshScratchPad(OneWire *ow, const uint8_t id[8], uint16_t addr, const uint8_t data[8]) -{ - uint8_t buf[11]; - uint8_t crc[2]; - int len = 0; - - // reset and select - if (!ResetAndSelect(ow, id)) { - return false; - } - - // perform refresh scratchpad command - buf[len++] = CMD_REFRESH_SCRATCHPAD; - buf[len++] = (addr >> 0) & 0xFF; // 2 byte target address - buf[len++] = (addr >> 8) & 0xFF; // 2 byte target address - memcpy(buf + len, data, 8); - len += 8; - ow->write_bytes(buf, len); - ow->read_bytes(crc, 2); - - return ow->check_crc16(buf, len, crc); -} - -static bool ReadScratchPad(OneWire *ow, const uint8_t id[8], uint16_t *addr, uint8_t *es, uint8_t data[8]) -{ - uint8_t buf[12]; - uint8_t crc[2]; - int len = 0; - - // reset and select - if (!ResetAndSelect(ow, id)) { - return false; - } - - // send read scratchpad command - buf[len++] = CMD_READ_SCRATCHPAD; - ow->write_bytes(buf, len); - - // get TA0/1 and ES - ow->read_bytes(buf + len, 3); - len += 3; - *addr = (buf[2] << 8) | buf[1]; - *es = buf[3]; - - // get data - ow->read_bytes(buf + len, 8); - len += 8; - memcpy(data, buf + 4, 8); - - // check CRC - ow->read_bytes(crc, 2); - return ow->check_crc16(buf, len, crc); -} - -static bool CopyScratchPad(OneWire *ow, const uint8_t id[8], uint16_t addr, uint8_t es, const uint8_t mac[20]) -{ - uint8_t buf[4]; - int len = 0; - uint8_t status; - - // reset and select - if (!ResetAndSelect(ow, id)) { - return false; - } - - // send copy scratchpad command + arguments - buf[len++] = CMD_COPY_SCRATCHPAD; - buf[len++] = (addr >> 0) & 0xFF; // 2 byte target address - buf[len++] = (addr >> 8) & 0xFF; // 2 byte target address - buf[len++] = es; // es - ow->write_bytes(buf, len, 1); // write and keep powered - - // wait while MAC is calculated - delay(T_CSHA); - - // send MAC - ow->write_bytes(mac, 20); - - // wait 10 ms - delay(T_PROG); - ow->depower(); - - // check final status byte - status = ow->read(); - return (status == 0xAA); -} - -static bool ReadAuthPage(OneWire *ow, const uint8_t id[8], uint16_t addr, uint8_t data[32], uint8_t mac[20]) -{ - uint8_t buf[36]; - uint8_t crc[2]; - uint8_t status; - int len = 0; - - // reset and select - if (!ResetAndSelect(ow, id)) { - return false; - } - - // send command - buf[len++] = CMD_READ_AUTH_PAGE; - buf[len++] = (addr >> 0) & 0xFF; - buf[len++] = (addr >> 8) & 0xFF; - ow->write_bytes(buf, len); - - // read data part + 0xFF - ow->read_bytes(buf + len, 33); - len += 33; - if (buf[35] != 0xFF) { - return false; - } - ow->read_bytes(crc, 2); - if (!ow->check_crc16(buf, len, crc)) { - return false; - } - memcpy(data, buf + 3, 32); - - // read mac part - delay(T_CSHA); - ow->read_bytes(mac, 20); - ow->read_bytes(crc, 2); - if (!ow->check_crc16(mac, 20, crc)) { - return false; - } - - // check final status byte - status = ow->read(); - return (status == 0xAA); -} - -static bool LoadFirstSecret(OneWire *ow, const uint8_t id[8], uint16_t addr, uint8_t es) -{ - uint8_t status; - - // reset and select - if (!ResetAndSelect(ow, id)) { - return false; - } - - // write auth code - ow->write(CMD_LOAD_FIRST_SECRET); - ow->write((addr >> 0) & 0xFF); - ow->write((addr >> 8) & 0xFF); - ow->write(es, 1); - delay(T_PROG); - ow->depower(); - - status = ow->read(); - return (status == 0xAA); -} - -static bool ReadMemory(OneWire *ow, const uint8_t id[8], int addr, int len, uint8_t data[]) -{ - // reset and select - if (!ResetAndSelect(ow, id)) { - return false; - } - - // write command/addr - ow->write(CMD_READ_MEMORY); - ow->write((addr >> 0) & 0xFF); - ow->write((addr >> 8) & 0xFF); - - // read data - ow->read_bytes(data, len); - - return true; -} - -bool DS1961::ReadAuthWithChallenge(const uint8_t id[8], uint16_t addr, const uint8_t challenge[3], uint8_t data[32], uint8_t mac[20]) -{ - uint8_t scratchpad[8]; - - // put the challenge in the scratchpad - memset(scratchpad, 0, sizeof(scratchpad)); - memcpy(scratchpad + 4, challenge, 3); - if (!WriteScratchPad(ow, id, addr, scratchpad)) { -// Serial.println("WriteScratchPad failed!"); - return false; - } - - // perform the authenticated read - if (!ReadAuthPage(ow, id, addr, data, mac)) { -// Serial.println("ReadAuthPage failed!"); - return false; - } - - return true; -} - -bool DS1961::WriteSecret(const uint8_t id[8], const uint8_t secret[8]) -{ - uint16_t addr; - uint8_t es; - uint8_t data[8]; - - // write secret to scratch pad - if (!WriteScratchPad(ow, id, MEM_SECRET, secret)) { -// Serial.println("WriteScratchPad failed!"); - return false; - } - - // read scratch pad for auth code - if (!ReadScratchPad(ow, id, &addr, &es, data)) { -// Serial.println("ReadScratchPad failed!"); - return false; - } - if (!LoadFirstSecret(ow, id, addr, es)) { -// Serial.println("LoadFirstSecret failed!"); - return false; - } - - return true; -} - -/* - * Writes 8 bytes of data to specified address - */ -bool DS1961::WriteData(const uint8_t id[8], int addr, const uint8_t data[8], const uint8_t mac[20]) -{ - uint8_t spad[8]; - uint16_t ad; - uint8_t es; - - // write data into scratchpad - if (!WriteScratchPad(ow, id, addr, data)) { - Serial.println("WriteScratchPad failed!"); - return false; - } - - // read scratch pad for auth code - if (!ReadScratchPad(ow, id, &ad, &es, spad)) { - Serial.println("ReadScratchPad failed!"); - return false; - } - - // copy scratchpad to EEPROM - if (!CopyScratchPad(ow, id, ad, es, mac)) { - Serial.println("CopyScratchPad failed!"); - return false; - } - - // refresh scratchpad - if (!RefreshScratchPad(ow, id, addr, data)) { - Serial.println("RefreshScratchPad failed!"); - return false; - } - - // re-write with load first secret - if (!LoadFirstSecret(ow, id, addr, es)) { - Serial.println("LoadFirstSecret failed!"); - return false; - } - - return true; -} - diff --git a/bitlair_doorduino_inner/src/ds1961.h b/bitlair_doorduino_inner/src/ds1961.h deleted file mode 100644 index 27179df..0000000 --- a/bitlair_doorduino_inner/src/ds1961.h +++ /dev/null @@ -1,23 +0,0 @@ -#ifndef _DS1961_H_ -#define _DS1961_H_ - -#include -#include - -#include "OneWire.h" - -class DS1961 { - -public: - DS1961(OneWire *oneWire); - - bool WriteSecret(const uint8_t id[8], const uint8_t secret[8]); - bool ReadAuthWithChallenge(const uint8_t id[8], uint16_t addr, const uint8_t challenge[3], uint8_t data[32], uint8_t mac[20]); - bool WriteData(const uint8_t id[8], int addr, const uint8_t data[8], const uint8_t mac[20]); - -private: - OneWire *ow; - -}; - -#endif /* _DS1961_H_ */ diff --git a/bitlair_doorduino_inner/src/main.cpp b/bitlair_doorduino_inner/src/main.cpp deleted file mode 100644 index 94f4094..0000000 --- a/bitlair_doorduino_inner/src/main.cpp +++ /dev/null @@ -1,741 +0,0 @@ -#include "OneWire.h" -#include "ds1961.h" - -#include -#include -// #include -#include "Entropy.h" -#include "sha1.h" -#include "Wire.h" - - -#include -// Motor steps per revolution. Most steppers are 200 steps or 1.8 degrees/step -#define MOTOR_STEPS 2 -#define RPM 60 -#define DIR A6 -// #define STEP A7 -#define STEP 9 -#include "A4988.h" -A4988 stepper(MOTOR_STEPS, DIR, STEP); - -#define INPUT_SOLENOID 7 -#define INPUT_HORN 3 -#define PIN_LEDSOLENOID 6 -#define PIN_LEDHORN 5 -bool StateSolenoid = false; -bool StateHorn = false; -uint32_t SolenoidStartTime; -bool StateSolenoidInactive = false; -uint32_t SolenoidInactiveStartTime; - - - -#define PIN_DOORPOWER A1 -#define PIN_SOLENOID A3 -#define PIN_HORN A2 -#define PIN_OPEN 13 -#define PIN_CLOSE A0 - -#define PIN_1WIRE 8 -#define PIN_LEDGREEN 10 -#define PIN_LEDRED 11 - -#define PIN_MAINS_POWER 2 - -#define CMD_BUFSIZE 64 -#define CMD_TIMEOUT 10000 //command timeout in milliseconds - -#define SECRETSIZE 8 -#define ADDRSIZE 8 -#define STORAGESIZE (SECRETSIZE + ADDRSIZE) -#define EEPROMDEVICEADDRESS 0x50 -#define EEPROMSIZE 2048 -#define SHA1SIZE 20 - -#define IBUTTON_SEARCH_TIMEOUT 60000 //timeout searching for ibutton - -#define LEDState_Off 0 -#define LEDState_Reading 1 -#define LEDState_Authorized 2 -#define LEDState_Busy 3 - -#define SPACEState_Open 1 -#define SPACEState_Closed 0 - -#define htons(x) ( ((x)<<8) | (((x)>>8)&0xFF) ) -#define ntohs(x) htons(x) - -#define htonl(x) ( ((x)<<24 & 0xFF000000UL) | \ - ((x)<< 8 & 0x00FF0000UL) | \ - ((x)>> 8 & 0x0000FF00UL) | \ - ((x)>>24 & 0x000000FFUL) ) -#define ntohl(x) htonl(x) - -OneWire ds(PIN_1WIRE); -DS1961 ibutton(&ds); - -bool HasMainsPower(); - -int Serialprintf (const char* fmt, ...) __attribute__ ((format (printf, 1, 2))); - -int Serialprintf (const char* fmt, ...) -{ - char buf[256]; - - va_list args; - va_start(args, fmt); - vsnprintf(buf, sizeof(buf), fmt, args); - va_end(args); - - Serial.print(buf); -} - -uint8_t g_ledstate = LEDState_Off; -uint32_t g_ledtimestart; -bool g_fade; -bool g_lockopen; -bool g_spacestate = SPACEState_Closed; - -#define LED_PERIOD 1024 - -void ProcessLEDs() -{ - if (g_ledstate == LEDState_Off) - { - analogWrite(PIN_LEDGREEN, 0); - analogWrite(PIN_LEDRED, 0); - } - else if (g_ledstate == LEDState_Reading) - { - uint32_t timesincesetting = millis() + LED_PERIOD / 2 - g_ledtimestart; - uint32_t ledtime = timesincesetting % LED_PERIOD; - uint32_t ledval; - if (ledtime < LED_PERIOD / 2) - ledval = ledtime; - else - ledval = (LED_PERIOD - 1) - ledtime; - - ledval = (ledval * ledval) / LED_PERIOD; - if (!HasMainsPower()) - ledval = (ledval + 5) / 10; - - if (g_lockopen) - { - analogWrite(PIN_LEDGREEN, ledval); - analogWrite(PIN_LEDRED, 0); - } - else - { - analogWrite(PIN_LEDGREEN, 0); - analogWrite(PIN_LEDRED, ledval); - } - } - else if (g_ledstate == LEDState_Authorized) - { - if (g_lockopen) - { - analogWrite(PIN_LEDGREEN, 255); - analogWrite(PIN_LEDRED, 0); - } - else - { - analogWrite(PIN_LEDGREEN, 0); - analogWrite(PIN_LEDRED, 255); - } - } - else if (g_ledstate == LEDState_Busy) - { - analogWrite(PIN_LEDGREEN, 255); - analogWrite(PIN_LEDRED, 255); - } -} - -void SetLEDState(uint8_t ledstate) -{ - if (ledstate == LEDState_Reading && g_ledstate != LEDState_Reading) - { - g_ledtimestart = millis(); - g_fade = true; - } - - g_ledstate = ledstate; - - ProcessLEDs(); -} - -void DelayLEDs(uint32_t delayms) -{ - uint32_t now = millis(); - while (millis() - now < delayms) - ProcessLEDs(); -} - -void setup() -{ - Serial.begin(115200); - Serial.println("DEBUG: Board started"); - Wire.begin(); - - stepper.begin(RPM); - stepper.enable(); - stepper.setMicrostep(1); // Set microstep mode to 1:1 - - pinMode(INPUT_SOLENOID, INPUT_PULLUP); - pinMode(INPUT_HORN, INPUT_PULLUP); - pinMode(PIN_LEDSOLENOID, OUTPUT); - pinMode(PIN_LEDHORN, OUTPUT); - pinMode(PIN_DOORPOWER, OUTPUT); - pinMode(PIN_SOLENOID, OUTPUT); - pinMode(PIN_OPEN, OUTPUT); - pinMode(PIN_CLOSE, OUTPUT); - pinMode(PIN_HORN, OUTPUT); - - pinMode(PIN_LEDGREEN, OUTPUT); - pinMode(PIN_LEDRED, OUTPUT); - pinMode(PIN_MAINS_POWER, INPUT); - - digitalWrite(PIN_OPEN, LOW); - digitalWrite(PIN_CLOSE, LOW); - digitalWrite(PIN_DOORPOWER, LOW); - digitalWrite(PIN_HORN, LOW); - digitalWrite(PIN_SOLENOID, LOW); - - SetLEDState(LEDState_Off); - - Entropy.initialize(); -} - -void writeEEPROM(unsigned int eeaddress, byte data ) -{ - Wire.beginTransmission(EEPROMDEVICEADDRESS); - Wire.write((int)(eeaddress >> 8)); // MSB - Wire.write((int)(eeaddress & 0xFF)); // LSB - Wire.write(data); - Wire.endTransmission(); - - delay(5); -} - -byte readEEPROM(unsigned int eeaddress ) -{ - byte rdata = 0xFF; - - Wire.beginTransmission(EEPROMDEVICEADDRESS); - Wire.write((int)(eeaddress >> 8)); // MSB - Wire.write((int)(eeaddress & 0xFF)); // LSB - Wire.endTransmission(); - - Wire.requestFrom(EEPROMDEVICEADDRESS,1); - - if (Wire.available()) rdata = Wire.read(); - - return rdata; -} - -void AddButton(uint8_t* addr, uint8_t* secret) -{ - for (uint16_t i = 0; i < EEPROMSIZE / STORAGESIZE; i++) - { - bool emptyslot = true; - uint16_t startaddr = i * STORAGESIZE; - for (uint16_t j = 0; j < ADDRSIZE; j++) - { - uint8_t eeprombyte = readEEPROM(startaddr + j); - if (eeprombyte != 0xFF && eeprombyte != addr[j]) - { - emptyslot = false; - break; - } - } - - if (emptyslot) - { - for (uint16_t j = 0; j < ADDRSIZE; j++) - writeEEPROM(startaddr + j, addr[j]); - - for (uint16_t j = 0; j < SECRETSIZE; j++) - writeEEPROM(startaddr + j + ADDRSIZE, secret[j]); - - Serialprintf("DEBUG: stored button in slot %i\n", i); - - return; - } - } - - Serial.println("ERROR: no room in eeprom to store button"); -} - -void RemoveButton(uint8_t* addr) -{ - for (uint16_t i = 0; i < EEPROMSIZE / STORAGESIZE; i++) - { - uint16_t startaddr = i * STORAGESIZE; - bool sameaddr = true; - for (uint16_t j = 0; j < ADDRSIZE; j++) - { - uint8_t eeprombyte = readEEPROM(startaddr + j); - if (eeprombyte != addr[j]) - { - sameaddr = false; - break; - } - } - if (!sameaddr) - continue; - - Serialprintf("DEBUG: erasing slot %i\n", i); - - for (uint16_t j = 0; j < STORAGESIZE; j++) - writeEEPROM(startaddr + j, 0xFF); - } -} - -bool GetButtonSecret(uint8_t* addr, uint8_t* secret) -{ - for (uint16_t i = 0; i < EEPROMSIZE / STORAGESIZE; i++) - { - uint16_t startaddr = i * STORAGESIZE; - bool sameaddr = true; - bool isempty = true; - for (uint16_t j = 0; j < ADDRSIZE; j++) - { - uint8_t eeprombyte = readEEPROM(startaddr + j); - if (isempty && eeprombyte != 0xFF) - isempty = false; - - if (eeprombyte != addr[j]) - { - sameaddr = false; - break; - } - } - - if (isempty) - continue; - - if (sameaddr) - { - Serialprintf("DEBUG: getting secret from slot %i\n", i); - - for (uint16_t j = 0; j < SECRETSIZE; j++) - secret[j] = readEEPROM(startaddr + j + ADDRSIZE); - - return true; - } - } - - Serial.println("DEBUG: can't find secret for button"); - - return false; -} - -void ListButtons() -{ - Serial.println("button list start"); - - for (uint16_t i = 0; i < EEPROMSIZE / STORAGESIZE; i++) - { - uint16_t startaddr = i * STORAGESIZE; - uint8_t buttonid[ADDRSIZE]; - bool isempty = true; - for (uint16_t j = 0; j < ADDRSIZE; j++) - { - uint8_t eeprombyte = readEEPROM(startaddr + j); - if (isempty && eeprombyte != 0xFF) - isempty = false; - - buttonid[j] = eeprombyte; - } - - if (isempty) - continue; - - Serialprintf("button: "); - for (uint16_t j = 0; j < ADDRSIZE; j++) - Serialprintf("%02x", buttonid[j]); - Serialprintf("\n"); - } -} - -#define RANDOMDELAY_MIN 50 -#define RANDOMDELAY_MAX 200 - -bool AuthenticateButton(uint8_t* addr) -{ - uint8_t secret[SECRETSIZE]; - if (!GetButtonSecret(addr, secret)) - return false; - - uint8_t mac_from_ibutton[SHA1SIZE]; - uint8_t data[32]; - uint8_t nonce[3]; - - for (uint8_t i = 0; i < sizeof(nonce); i++) - nonce[i] = Entropy.randomByte(); - - if (!ibutton.ReadAuthWithChallenge(addr, 0, nonce, data, mac_from_ibutton)) - return false; - - sha1::sha1nfo sha1data = {}; - sha1::sha1_init(&sha1data); - sha1::sha1_write(&sha1data, (const char*)secret, 4); - sha1::sha1_write(&sha1data, (const char*)data, sizeof(data)); - sha1::sha1_writebyte(&sha1data, 0xff); - sha1::sha1_writebyte(&sha1data, 0xff); - sha1::sha1_writebyte(&sha1data, 0xff); - sha1::sha1_writebyte(&sha1data, 0xff); - sha1::sha1_writebyte(&sha1data, 0x40); - sha1::sha1_write(&sha1data, (const char*)addr, ADDRSIZE - 1); - sha1::sha1_write(&sha1data, (const char*)secret + 4, 4); - sha1::sha1_write(&sha1data, (const char*)nonce, sizeof(nonce)); - - uint8_t* sha_computed = sha1::sha1_result(&sha1data); - - uint8_t mac_computed[SHA1SIZE]; - ((uint32_t*)mac_computed)[0] = htonl(ntohl(*(uint32_t *)sha_computed) - 0x67452301); - ((uint32_t*)mac_computed)[1] = htonl(ntohl(*(uint32_t *)(sha_computed+4)) - 0xefcdab89); - ((uint32_t*)mac_computed)[2] = htonl(ntohl(*(uint32_t *)(sha_computed+8)) - 0x98badcfe); - ((uint32_t*)mac_computed)[3] = htonl(ntohl(*(uint32_t *)(sha_computed+12)) - 0x10325476); - ((uint32_t*)mac_computed)[4] = htonl(ntohl(*(uint32_t *)(sha_computed+16)) - 0xc3d2e1f0); - - //this check should always take the same amount of time, to prevent a timing attack - bool macvalid = true; - for (uint8_t i = 0; i < SHA1SIZE; i++) - { - if (mac_from_ibutton[i] != mac_computed[SHA1SIZE - 1 - i]) - macvalid = false; - } - - //add a random delay - delayMicroseconds(Entropy.random(RANDOMDELAY_MIN, RANDOMDELAY_MAX)); - - return macvalid; -} - -bool ReadCMD(char* cmdbuf, uint8_t* cmdbuffill) -{ - uint32_t cmdstarttime = millis(); - *cmdbuffill = 0; - for(;;) - { - if (Serial.available()) - { - char input = Serial.read(); - if (input == '\n') - { - cmdbuf[*cmdbuffill] = 0; - return true; - } - else if (*cmdbuffill < CMD_BUFSIZE - 1) - { - cmdbuf[*cmdbuffill] = input; - (*cmdbuffill)++; - } - } - - if (millis() - cmdstarttime >= CMD_TIMEOUT) - { - Serial.println("ERROR: timeout receiving command"); - return false; - } - } -} - -uint8_t NextWordPos(char* cmdbuf, uint8_t cmdbuffill, uint8_t index) -{ - bool foundwhitespace = false; - for (uint8_t i = index; i < cmdbuffill; i++) - { - if (!foundwhitespace) - { - if (cmdbuf[i] == ' ') - foundwhitespace = true; - } - else - { - if (cmdbuf[i] != ' ') - { - return i; - } - } - } - - return 0; -} - -bool GetHexWordFromCMD(char* cmdbuf, uint8_t cmdbuffill, uint8_t* wordpos, uint8_t* wordbuf, uint8_t wordsize, char* wordname) -{ - *wordpos = NextWordPos(cmdbuf, cmdbuffill, *wordpos); - - if (*wordpos == 0) - { - Serialprintf("ERROR: no %s found in command\n", wordname); - return false; - } - else if (cmdbuffill - *wordpos < wordsize * 2) - { - Serialprintf("ERROR: %s is too short\n", wordname); - return false; - } - - for (uint8_t i = 0; i < wordsize; i++) - { - if ((cmdbuf[*wordpos + i * 2] == ' ') || (cmdbuf[*wordpos + i * 2 + 1] == ' ')) - { - Serialprintf("ERROR: %s is too short\n", wordname); - return false; - } - - int numread = sscanf(cmdbuf + *wordpos + i * 2, "%2hhx", wordbuf + i); - if (numread != 1) - { - Serialprintf("ERROR: %s is invalid\n", wordname); - return false; - } - } - - return true; -} - -#define CMD_ADD_BUTTON "add_button" -#define CMD_REMOVE_BUTTON "remove_button" -#define CMD_LIST_BUTTONS "list_buttons" -#define CMD_SPACESTATE "spacestate" - -void ParseCMD(char* cmdbuf, uint8_t cmdbuffill) -{ - Serial.print("DEBUG: Received cmd: "); - Serial.println(cmdbuf); - - bool isadd = strncmp(CMD_ADD_BUTTON, cmdbuf, strlen(CMD_ADD_BUTTON)) == 0; - bool isremove = strncmp(CMD_REMOVE_BUTTON, cmdbuf, strlen(CMD_REMOVE_BUTTON)) == 0; - bool islist = strncmp(CMD_LIST_BUTTONS, cmdbuf, strlen(CMD_LIST_BUTTONS)) == 0; - bool isspacestate = strncmp(CMD_SPACESTATE, cmdbuf, strlen(CMD_SPACESTATE)) == 0; - - if (isadd || isremove) - { - uint8_t wordpos = 0; - uint8_t addr[ADDRSIZE]; - if (!GetHexWordFromCMD(cmdbuf, cmdbuffill, &wordpos, addr, ADDRSIZE, "address")) - return; - - Serial.print("DEBUG: Received address "); - for (uint8_t i = 0; i < ADDRSIZE; i++) - Serialprintf("%02x", addr[i]); - Serial.print("\n"); - - bool addrvalid = false; - for (uint8_t i = 0; i < ADDRSIZE; i++) - { - if (addr[i] != 0xFF) - { - addrvalid = true; - break; - } - } - if (!addrvalid) - { - Serial.println("ERROR: address FFFFFFFFFFFFFFFF is invalid"); - return; - } - - if (isadd) - { - uint8_t secret[SECRETSIZE]; - if (!GetHexWordFromCMD(cmdbuf, cmdbuffill, &wordpos, secret, SECRETSIZE, "secret")) - return; - - Serial.print("DEBUG: Received secret "); - for (uint8_t i = 0; i < ADDRSIZE; i++) - Serialprintf("%02x", secret[i]); - Serial.print("\n"); - - AddButton(addr, secret); - } - else - { - Serialprintf("DEBUG: removing button\n"); - RemoveButton(addr); - } - } - else if (islist) - { - ListButtons(); - } - else if (isspacestate) - { - uint8_t wordpos = 0; - wordpos = NextWordPos(cmdbuf, cmdbuffill, wordpos); - bool isopen = strncmp("open", &cmdbuf[wordpos], strlen("open")) == 0; - bool isclosed = strncmp("closed", &cmdbuf[wordpos], strlen("closed")) == 0; - if(isopen || isclosed){ - Serial.print("Old state: "); - Serial.println(g_spacestate == SPACEState_Open ? "open" : "closed"); - g_spacestate = isopen ? SPACEState_Open : SPACEState_Closed; - } - Serial.print("Current state: "); - Serial.println(g_spacestate == SPACEState_Open ? "open" : "closed"); - } - else - { - Serial.println("Unknown command"); - } -} - -#define TOGGLE_TIME 2500 -#define BUTTON_TIME 250 - -void ToggleLock() -{ - if (g_lockopen) - { - g_lockopen = false; - Serial.println("closing lock"); - digitalWrite(PIN_DOORPOWER, HIGH); - digitalWrite(PIN_CLOSE, HIGH); - DelayLEDs(BUTTON_TIME); - DelayLEDs(TOGGLE_TIME - BUTTON_TIME); - } - else - { - g_lockopen = true; - Serial.println("opening lock"); - digitalWrite(PIN_DOORPOWER, HIGH); - digitalWrite(PIN_OPEN, HIGH); - DelayLEDs(BUTTON_TIME); - DelayLEDs(TOGGLE_TIME - BUTTON_TIME); - } - - DelayLEDs(4000); - digitalWrite(PIN_OPEN, LOW); - digitalWrite(PIN_CLOSE, LOW); - digitalWrite(PIN_DOORPOWER, LOW); - - Serial.println("finished lock action"); -} - -bool HasMainsPower() -{ - return digitalRead(PIN_MAINS_POWER) == HIGH; -} - -void loop() -{ - uint8_t addr[ADDRSIZE]; - uint32_t deniedcount = 0; - - for(;;) - { - if (Serial.available()) - { - uint8_t input = Serial.read(); - if (input == '\n') - { - SetLEDState(LEDState_Busy); - Serial.println("ready"); - - char cmdbuf[CMD_BUFSIZE] = {}; - uint8_t cmdbuffill; - if (ReadCMD(cmdbuf, &cmdbuffill)) - ParseCMD(cmdbuf, cmdbuffill); - } - } - - SetLEDState(LEDState_Reading); - - ds.reset_search(); - if (ds.search(addr) && OneWire::crc8(addr, 7) == addr[7]) - { - Serial.print("DEBUG: Found iButton with address: "); - for (uint8_t i = 0; i < sizeof(addr); i++) - Serialprintf("%02x", addr[i]); - Serial.print('\n'); - - if (AuthenticateButton(addr)) - { - SetLEDState(LEDState_Authorized); - Serial.print("iButton authenticated\n"); - g_lockopen = true; - // DelayLEDs(5000); - // ToggleLock(); - deniedcount = 0; - - // if(g_lockopen == true){ - StateSolenoid = true; - SolenoidStartTime = millis(); - Serial.print("Solenoid activated\n"); - digitalWrite(PIN_SOLENOID, HIGH); - // stepper.move(MOTOR_STEPS*(RPM/60)*10); - // } - - } - else - { - deniedcount++; - if (deniedcount == 3) - { - Serial.print("iButton not authenticated\n"); - SetLEDState(LEDState_Busy); - //disabled because sounding the horn resets the arduino - //digitalWrite(PIN_HORN, HIGH); - //DelayLEDs(500); - //digitalWrite(PIN_HORN, LOW); - deniedcount = 0; - } - } - } - else - { - deniedcount = 0; - } - - ProcessLEDs(); - - if(g_spacestate == SPACEState_Open){ - digitalWrite(PIN_LEDSOLENOID, HIGH); - }else{ - digitalWrite(PIN_LEDSOLENOID, LOW); - } - digitalWrite(PIN_LEDHORN, HIGH); - if (digitalRead(INPUT_SOLENOID) == LOW) { - if(g_spacestate == SPACEState_Open){ - if(StateSolenoid == false){ - StateSolenoid = true; - SolenoidStartTime = millis(); - Serial.print("Solenoid activated\n"); - digitalWrite(PIN_SOLENOID, HIGH); - g_lockopen = true; - // stepper.move(MOTOR_STEPS*(RPM/60)*10); - } - }else{ - if(StateSolenoidInactive == false){ - StateSolenoidInactive = true; - SolenoidInactiveStartTime = millis(); - Serial.print("Spacestate closed, Solenoid button not active\n"); - } - } - } - if(StateSolenoid == true && ((millis() - SolenoidStartTime) > (5*1000)) ){ - digitalWrite(PIN_SOLENOID, LOW); - StateSolenoid = false; - g_lockopen = false; - } - if(StateSolenoidInactive == true && ((millis() - SolenoidInactiveStartTime) > (1*1000)) ){ - StateSolenoidInactive = false; - } - if (digitalRead(INPUT_HORN) == LOW) { - if(StateHorn == false){ - StateHorn = true; - Serial.print("Horn activated\n"); - digitalWrite(PIN_HORN, HIGH); - } - }else{ - StateHorn = false; - digitalWrite(PIN_HORN, LOW); - } - - - } -} - diff --git a/bitlair_doorduino_inner/src/sha1.cpp b/bitlair_doorduino_inner/src/sha1.cpp deleted file mode 100644 index e6dace5..0000000 --- a/bitlair_doorduino_inner/src/sha1.cpp +++ /dev/null @@ -1,156 +0,0 @@ -#include "sha1.h" -#include - -namespace sha1 -{ - /* code */ - #define SHA1_K0 0x5a827999 - #define SHA1_K20 0x6ed9eba1 - #define SHA1_K40 0x8f1bbcdc - #define SHA1_K60 0xca62c1d6 - - void sha1_init(sha1nfo *s) { - s->state[0] = 0x67452301; - s->state[1] = 0xefcdab89; - s->state[2] = 0x98badcfe; - s->state[3] = 0x10325476; - s->state[4] = 0xc3d2e1f0; - s->byteCount = 0; - s->bufferOffset = 0; - } - - uint32_t sha1_rol32(uint32_t number, uint8_t bits) { - return ((number << bits) | (number >> (32-bits))); - } - - void sha1_hashBlock(sha1nfo *s) { - uint8_t i; - uint32_t a,b,c,d,e,t; - - a=s->state[0]; - b=s->state[1]; - c=s->state[2]; - d=s->state[3]; - e=s->state[4]; - for (i=0; i<80; i++) { - if (i>=16) { - t = s->buffer[(i+13)&15] ^ s->buffer[(i+8)&15] ^ s->buffer[(i+2)&15] ^ s->buffer[i&15]; - s->buffer[i&15] = sha1_rol32(t,1); - } - if (i<20) { - t = (d ^ (b & (c ^ d))) + SHA1_K0; - } else if (i<40) { - t = (b ^ c ^ d) + SHA1_K20; - } else if (i<60) { - t = ((b & c) | (d & (b | c))) + SHA1_K40; - } else { - t = (b ^ c ^ d) + SHA1_K60; - } - t+=sha1_rol32(a,5) + e + s->buffer[i&15]; - e=d; - d=c; - c=sha1_rol32(b,30); - b=a; - a=t; - } - s->state[0] += a; - s->state[1] += b; - s->state[2] += c; - s->state[3] += d; - s->state[4] += e; - } - - void sha1_addUncounted(sha1nfo *s, uint8_t data) { - uint8_t * const b = (uint8_t*) s->buffer; - #ifdef SHA_BIG_ENDIAN - b[s->bufferOffset] = data; - #else - b[s->bufferOffset ^ 3] = data; - #endif - s->bufferOffset++; - if (s->bufferOffset == BLOCK_LENGTH) { - sha1_hashBlock(s); - s->bufferOffset = 0; - } - } - - void sha1_writebyte(sha1nfo *s, uint8_t data) { - ++s->byteCount; - sha1_addUncounted(s, data); - } - - void sha1_write(sha1nfo *s, const char *data, size_t len) { - for (;len--;) sha1_writebyte(s, (uint8_t) *data++); - } - - void sha1_pad(sha1nfo *s) { - // Implement SHA-1 padding (fips180-2 §5.1.1) - - // Pad with 0x80 followed by 0x00 until the end of the block - sha1_addUncounted(s, 0x80); - while (s->bufferOffset != 56) sha1_addUncounted(s, 0x00); - - // Append length in the last 8 bytes - sha1_addUncounted(s, 0); // We're only using 32 bit lengths - sha1_addUncounted(s, 0); // But SHA-1 supports 64 bit lengths - sha1_addUncounted(s, 0); // So zero pad the top bits - sha1_addUncounted(s, s->byteCount >> 29); // Shifting to multiply by 8 - sha1_addUncounted(s, s->byteCount >> 21); // as SHA-1 supports bitstreams as well as - sha1_addUncounted(s, s->byteCount >> 13); // byte. - sha1_addUncounted(s, s->byteCount >> 5); - sha1_addUncounted(s, s->byteCount << 3); - } - - uint8_t* sha1_result(sha1nfo *s) { - // Pad to complete the last block - sha1_pad(s); - - #ifndef SHA_BIG_ENDIAN - // Swap byte order back - int i; - for (i=0; i<5; i++) { - s->state[i]= - (((s->state[i])<<24)& 0xff000000) - | (((s->state[i])<<8) & 0x00ff0000) - | (((s->state[i])>>8) & 0x0000ff00) - | (((s->state[i])>>24)& 0x000000ff); - } - #endif - - // Return pointer to hash (20 characters) - return (uint8_t*) s->state; - } - - #define HMAC_IPAD 0x36 - #define HMAC_OPAD 0x5c - - void sha1_initHmac(sha1nfo *s, const uint8_t* key, int keyLength) { - uint8_t i; - memset(s->keyBuffer, 0, BLOCK_LENGTH); - if (keyLength > BLOCK_LENGTH) { - // Hash long keys - sha1_init(s); - for (;keyLength--;) sha1_writebyte(s, *key++); - memcpy(s->keyBuffer, sha1_result(s), HASH_LENGTH); - } else { - // Block length keys are used as is - memcpy(s->keyBuffer, key, keyLength); - } - // Start inner hash - sha1_init(s); - for (i=0; ikeyBuffer[i] ^ HMAC_IPAD); - } - } - - uint8_t* sha1_resultHmac(sha1nfo *s) { - uint8_t i; - // Complete inner hash - memcpy(s->innerHash,sha1_result(s),HASH_LENGTH); - // Calculate outer hash - sha1_init(s); - for (i=0; ikeyBuffer[i] ^ HMAC_OPAD); - for (i=0; iinnerHash[i]); - return sha1_result(s); - } -} diff --git a/bitlair_doorduino_inner/src/sha1.h b/bitlair_doorduino_inner/src/sha1.h deleted file mode 100644 index 2b1ddf9..0000000 --- a/bitlair_doorduino_inner/src/sha1.h +++ /dev/null @@ -1,69 +0,0 @@ -#ifndef SHA1_H -#define SHA1_H - -#include -#include - -#define __LITTLE_ENDIAN__ -//#define __BIG_ENDIAN__ - -namespace sha1 -{ - /* This code is public-domain - it is based on libcrypt - * placed in the public domain by Wei Dai and other contributors. - */ - // gcc -Wall -DSHA1TEST -o sha1test sha1.c && ./sha1test - - #ifdef __BIG_ENDIAN__ - # define SHA_BIG_ENDIAN - #elif defined __LITTLE_ENDIAN__ - /* override */ - #elif defined __BYTE_ORDER - # if __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__ - # define SHA_BIG_ENDIAN - # endif - #else // ! defined __LITTLE_ENDIAN__ - # include // machine/endian.h - # if __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__ - # define SHA_BIG_ENDIAN - # endif - #endif - - - /* header */ - - #define HASH_LENGTH 20 - #define BLOCK_LENGTH 64 - - typedef struct sha1nfo { - uint32_t buffer[BLOCK_LENGTH/4]; - uint32_t state[HASH_LENGTH/4]; - uint32_t byteCount; - uint8_t bufferOffset; - uint8_t keyBuffer[BLOCK_LENGTH]; - uint8_t innerHash[HASH_LENGTH]; - } sha1nfo; - - /* public API - prototypes - TODO: doxygen*/ - - /** - */ - void sha1_init(sha1nfo *s); - /** - */ - void sha1_writebyte(sha1nfo *s, uint8_t data); - /** - */ - void sha1_write(sha1nfo *s, const char *data, size_t len); - /** - */ - uint8_t* sha1_result(sha1nfo *s); - /** - */ - void sha1_initHmac(sha1nfo *s, const uint8_t* key, int keyLength); - /** - */ - uint8_t* sha1_resultHmac(sha1nfo *s); -} - -#endif //SHA1_H diff --git a/bitlair_doorduino_inner/test/README b/bitlair_doorduino_inner/test/README deleted file mode 100644 index e7d1588..0000000 --- a/bitlair_doorduino_inner/test/README +++ /dev/null @@ -1,11 +0,0 @@ - -This directory is intended for PlatformIO Unit Testing and project tests. - -Unit Testing is a software testing method by which individual units of -source code, sets of one or more MCU program modules together with associated -control data, usage procedures, and operating procedures, are tested to -determine whether they are fit for use. Unit testing finds problems early -in the development cycle. - -More information about PlatformIO Unit Testing: -- https://docs.platformio.org/page/plus/unit-testing.html diff --git a/manage.py b/manage.py index dea27fb..ee9cbc9 100755 --- a/manage.py +++ b/manage.py @@ -4,7 +4,7 @@ import serial import sys import time -SERIAL_PORTS = [ '/dev/ttyS2' ] +SERIAL_PORTS = [ '/dev/ttyS1', '/dev/ttyS2' ] def open_port(tty): @@ -56,7 +56,7 @@ def remove_button(ports, button): break print(line) -def add_button(ports, button, secret): +def add_button(ser, button, secret): for port in ports: with open_port(port) as ser: ser.write(b'\r\n') diff --git a/pi-config/.gitignore b/pi-config/.gitignore deleted file mode 100644 index 344e05d..0000000 --- a/pi-config/.gitignore +++ /dev/null @@ -1,2 +0,0 @@ -toegang -config/settings diff --git a/pi-config/config/settings-example b/pi-config/config/settings-example deleted file mode 100644 index 8334d6e..0000000 --- a/pi-config/config/settings-example +++ /dev/null @@ -1,13 +0,0 @@ -[mqtt] -doorbell.subject=bitlair/doorduino/doorbell -dooropen.subject=bitlair/doorduino/dooropen -lockstate.subject=bitlair/doorduino/lockstate -server=mqtt.bitlair.nl -mqtt-simple=/usr/local/bin/mqtt-simple -client-id=doorpi -state-bitlair.subject=bitlair/state -state-djo.subject=bitlair/state/djo - -[serial] -device=/dev/ttyS2 - diff --git a/pi-config/doorduino-init b/pi-config/doorduino-init deleted file mode 100755 index 19f1acc..0000000 --- a/pi-config/doorduino-init +++ /dev/null @@ -1,111 +0,0 @@ -#!/bin/sh -### BEGIN INIT INFO -# Provides: generic-prog -# Required-Start: $local_fs $remote_fs $network -# Required-Stop: $local_fs $remote_fs $network -# Default-Start: 2 3 4 5 -# Default-Stop: 0 1 6 -# Short-Description: Generic Program -# Description: Generic Program is a generic program to do generic things with -### END INIT INFO - - -# Documentation available at -# http://refspecs.linuxfoundation.org/LSB_3.1.0/LSB-Core-generic/LSB-Core-generic/iniscrptfunc.html -# Debian provides some extra functions though -. /lib/lsb/init-functions - - -DAEMON_NAME="root" -DAEMON_USER="root" -DAEMON_PATH="/root/bitlair_doorduino/pi-config/doorduino.py" -DAEMON_OPTS="-c /root/bitlair_doorduino/pi-config/config" -DAEMON_PWD="${PWD}" -DAEMON_DESC=$(get_lsb_header_val $0 "Short-Description") -DAEMON_PID="/var/run/${DAEMON_NAME}.pid" -DAEMON_NICE=0 -DAEMON_LOG='/var/log/doorduino' - -[ -r "/etc/default/${DAEMON_NAME}" ] && . "/etc/default/${DAEMON_NAME}" - -do_start() { - local result - - pidofproc -p "${DAEMON_PID}" "${DAEMON_PATH}" > /dev/null - if [ $? -eq 0 ]; then - log_warning_msg "${DAEMON_NAME} is already started" - result=0 - else - log_daemon_msg "Starting ${DAEMON_DESC}" "${DAEMON_NAME}" - touch "${DAEMON_LOG}" - chown $DAEMON_USER "${DAEMON_LOG}" - chmod u+rw "${DAEMON_LOG}" - if [ -z "${DAEMON_USER}" ]; then - start-stop-daemon --start --quiet --oknodo --background \ - --nicelevel $DAEMON_NICE \ - --chdir "${DAEMON_PWD}" \ - --pidfile "${DAEMON_PID}" --make-pidfile \ - --exec "${DAEMON_PATH}" -- $DAEMON_OPTS - result=$? - else - start-stop-daemon --start --quiet --oknodo --background \ - --nicelevel $DAEMON_NICE \ - --chdir "${DAEMON_PWD}" \ - --pidfile "${DAEMON_PID}" --make-pidfile \ - --chuid "${DAEMON_USER}" \ - --exec "${DAEMON_PATH}" -- $DAEMON_OPTS - result=$? - fi - log_end_msg $result - fi - return $result -} - -do_stop() { - local result - - pidofproc -p "${DAEMON_PID}" "${DAEMON_PATH}" > /dev/null - if [ $? -ne 0 ]; then - log_warning_msg "${DAEMON_NAME} is not started" - result=0 - else - log_daemon_msg "Stopping ${DAEMON_DESC}" "${DAEMON_NAME}" - killproc -p "${DAEMON_PID}" "${DAEMON_PATH}" - result=$? - log_end_msg $result - rm "${DAEMON_PID}" - fi - return $result -} - -do_restart() { - local result - do_stop - result=$? - if [ $result = 0 ]; then - do_start - result=$? - fi - return $result -} - -do_status() { - local result - status_of_proc -p "${DAEMON_PID}" "${DAEMON_PATH}" "${DAEMON_NAME}" - result=$? - return $result -} - -do_usage() { - echo $"Usage: $0 {start | stop | restart | status}" - exit 1 -} - -case "$1" in -start) do_start; exit $? ;; -stop) do_stop; exit $? ;; -restart) do_restart; exit $? ;; -status) do_status; exit $? ;; -*) do_usage; exit 1 ;; -esac - diff --git a/pi-config/doorduino.py b/pi-config/doorduino.py deleted file mode 100755 index 1abfa0f..0000000 --- a/pi-config/doorduino.py +++ /dev/null @@ -1,320 +0,0 @@ -#!/usr/bin/python3 - -from serial.tools import list_ports -import serial -import io -import time -import subprocess -import csv -import getopt -import sys -import os -import math -import paramiko -from pathlib import Path -import configparser -import re -import threading -import syslog -import csv -import git - -import logging -from paho.mqtt import client as mqtt_client - -def connect_mqtt(config, broker, port, client_id): - # def on_connect(client, userdata, flags, rc): - # For paho-mqtt 2.0.0, you need to add the properties parameter. - def on_connect(client, userdata, flags, rc, properties): - if rc == 0: - print("Connected to MQTT Broker!") - subscribe(client, config.get('mqtt', 'state-bitlair.subject')) - subscribe(client, config.get('mqtt', 'state-djo.subject')) - else: - print("Failed to connect, return code %d\n", rc) - # Set Connecting Client ID - # For paho-mqtt 2.0.0, you need to set callback_api_version. - client = mqtt_client.Client(client_id=client_id, callback_api_version=mqtt_client.CallbackAPIVersion.VERSION2) - - # client.username_pw_set(username, password) - client.on_connect = on_connect - client.connect(broker, port) - return client - -FIRST_RECONNECT_DELAY = 1 -RECONNECT_RATE = 2 -MAX_RECONNECT_COUNT = 12 -MAX_RECONNECT_DELAY = 60 - -def on_disconnect(client, userdata, rc): - logging.info("Disconnected with result code: %s", rc) - reconnect_count, reconnect_delay = 0, FIRST_RECONNECT_DELAY - while reconnect_count < MAX_RECONNECT_COUNT: - logging.info("Reconnecting in %d seconds...", reconnect_delay) - time.sleep(reconnect_delay) - - try: - client.reconnect() - logging.info("Reconnected successfully!") - return - except Exception as err: - logging.error("%s. Reconnect failed. Retrying...", err) - - reconnect_delay *= RECONNECT_RATE - reconnect_delay = min(reconnect_delay, MAX_RECONNECT_DELAY) - reconnect_count += 1 - logging.info("Reconnect failed after %s attempts. Exiting...", reconnect_count) - -states = {} -def update_spacestate(): - global ser - open = False - for key in states: - if states[key] == "open": - open = True - try: - if open: - print("Send spacestate open") - ser.write(b"\n") - ser.write(b"spacestate open\n"); - else: - print("Send spacestate closed") - ser.write(b"\n") - ser.write(b"spacestate closed\n") - except serial.SerialException: - print("Serial connection error") - time.sleep(2) - - -def subscribe(client: mqtt_client, topic): - def on_message(client, userdata, msg): - states[msg.topic] = msg.payload.decode() - print(f"Received `{msg.payload.decode()}` from `{msg.topic}` topic") - update_spacestate() - - client.subscribe(topic) - client.on_message = on_message - - -def read_configuration(configdir): - if (configdir == ''): - print("Missing configdir.") - sys.exit(2) - - if not os.path.exists(configdir): - print("Directory ", configdir, " does not exist"); - sys.exit(2) - - configfile = Path(os.path.join(configdir, 'settings')) - if not configfile.is_file(): - print(configfile, " does not exist") - sys.exit(2) - - config = configparser.ConfigParser() - config.read_file(configfile.open()) - - expected_config_options = { 'mqtt': [ 'doorbell.subject', 'dooropen.subject', 'lockstate.subject', 'server', 'mqtt-simple' ], - 'serial': [ 'device' ] } - - for section, options in expected_config_options.items(): - for option in options: - if not config.has_option(section, option): - print("Missing config option ", option, "in section", section) - sys.exit(2) - - return config - -def mqtt_send_thread(config, subject, value, persistent): - if persistent: - subprocess.call([config.get('mqtt', 'mqtt-simple'), "-h", config.get('mqtt', 'server'), "-r", "-p", subject, "-m", value]) - else: - subprocess.call([config.get('mqtt', 'mqtt-simple'), "-h", config.get('mqtt', 'server'), "-p", subject, "-m", value]) - -def mqtt(config, subject, value, persistent=False): - threading.Thread(target = mqtt_send_thread, args = (config, subject, value, persistent)).start() - -def log(message): - print("LOG " + message) - syslog.syslog(message) - -def mqtt_thread(): - global client - global config - client = connect_mqtt(config, config.get('mqtt', 'server'), 1883, config.get('mqtt', 'client-id')) - - client.loop_forever() - -buttons = [] -def serial_monitor_thread(): - global ser - global config - global buttons - while True: - try: - ser = serial.Serial(config.get('serial', 'device'), 115200, rtscts=False, dsrdtr=True) - - time.sleep(2); - print("Doorduino started"); - - while True: - data = ser.readline() - action = data.decode("iso-8859-1").strip() - - print("Data:" + action) - if action == "Horn activated": - print("Horn activated") - log("Horn activated") - mqtt(config, config.get('mqtt','doorbell.subject'), '1', False) - time.sleep(2) - mqtt(config, config.get('mqtt','doorbell.subject'), '0', False) - elif action == "Solenoid activated": - print("Solenoid activated") - log("Solenoid activated") - mqtt(config, config.get('mqtt','dooropen.subject'), '1', False) - time.sleep(2) - mqtt(config, config.get('mqtt','dooropen.subject'), '0', False) - elif action == "iButton authenticated": - print("iButton authenticated") - log("iButton authenticated") - elif action == "opening lock": - print("lock open") - log("lock open") - mqtt(config, config.get('mqtt','lockstate.subject'), 'open', True) - elif action == "closing lock": - print("lock closed") - log("lock closed") - mqtt(config, config.get('mqtt','lockstate.subject'), 'closed', True) - elif action[:7] == "button:": - # print("got button ") - # print(action[8:]) - if not action[8:] in buttons: - buttons.append(action[8:]) - elif action == "DEBUG: Board started": - print("Arduino was reset, sending spacestate") - update_spacestate() - - except serial.SerialException: - print("Serial connection error") - time.sleep(2) - except StopIteration: - print("No device found") - time.sleep(2) - - -def git_update(git_dir): - log("Updating git") - # subprocess.call(["git", "-C", git_dir, "pull"]) - repo = git.Repo(git_dir) - # print('Remotes:') - # for remote in repo.remotes: - # print(f'- {remote.name} {remote.url}') - try: - pull = repo.remotes.origin.pull() - except git.exc.GitCommandError: - print("Git pull failed") - return False - - # if pull[0].flags == 128: - # print("Git pull failed") - # return False - return True - - -def update_buttons(): - global ser - global buttons - print("GIT init") - if(not git_update("toegang")): - print("Aborting GIT update thread") - return False - - git_buttons = {} - with open('toegang/toegang.csv', newline='') as csvfile: - data = csvfile.read() - data = data.replace(' ', '') - reader = csv.DictReader(data.splitlines(), delimiter=',') - for row in reader: - ibutton = row['ibutton'].split(':') - git_buttons[ibutton[0].lower()] = ibutton[1].lower() - # print(row['naam'] + " " + row['ibutton']) - - if len(git_buttons) < 25: - print("Something wrong, not enough buttons in git") - return - - buttons = [] - ser.write(b"\n") - ser.write(b"list_buttons\n"); - time.sleep(10) - if len(buttons) < 5: - print("Something wrong, not enough buttons in doorduino") - return - - print(buttons) - for button in git_buttons: - if button not in buttons: - print("should add " + button) - ser.write(b"\n") - ser.write(b"add_button "+button.encode('ascii')+b" "+git_buttons[button].encode('ascii')+b"\n") - time.sleep(2) - # else: - # print("already there " + button) - - for button in buttons: - if button not in git_buttons: - print("should remove " + button) - ser.write(b"\n") - ser.write(b"remove_button "+button.encode('ascii')+b"\n") - time.sleep(2) - # else: - # print("should be there " + button) - - print("Update buttons finished") - - -def git_thread(): - print("Updating buttons") - update_buttons() - print("Update buttons finished, sleeping for 3600 seconds") - time.sleep(3600) - - -def threadwrap(threadfunc): - def wrapper(): - while True: - try: - threadfunc() - except BaseException as e: - print('{!r}; restarting thread'.format(e)) - else: - print('exited normally, bad thread; restarting') - return wrapper - - -def main(argv): - global config - configdir = '' - - syslog.openlog('doorduino') - - try: - opts, args = getopt.getopt(argv,"c:",["config="]) - except getopt.GetoptError: - print('doorduino.py -c ') - sys.exit(2) - - for opt, arg in opts: - if opt == "-c" or opt == "--config": - configdir = arg - - config = read_configuration(configdir) - - threading.Thread(target = threadwrap(serial_monitor_thread)).start() - time.sleep(5) # Give doorduino time to start before sending spacestate data - threading.Thread(target = threadwrap(mqtt_thread)).start() - threading.Thread(target = threadwrap(git_thread)).start() - - -if __name__ == "__main__": - main(sys.argv[1:]) - diff --git a/pi-config/doorduino.service b/pi-config/doorduino.service deleted file mode 100644 index c06cd09..0000000 --- a/pi-config/doorduino.service +++ /dev/null @@ -1,13 +0,0 @@ -[Unit] -Description=Doorduino -After=network.target - -[Service] -Type=idle -Restart=on-failure -User=root -WorkingDirectory=/root/bitlair_doorduino/pi-config -ExecStart=/usr/bin/python3 -u doorduino.py -c config - -[Install] -WantedBy=multi-user.target \ No newline at end of file diff --git a/pi-config/requirements.txt b/pi-config/requirements.txt deleted file mode 100644 index 2b40728..0000000 --- a/pi-config/requirements.txt +++ /dev/null @@ -1,3 +0,0 @@ -paho-mqtt -paramiko -GitPython diff --git a/pi-config/reset_arduino.sh b/pi-config/reset_arduino.sh deleted file mode 100755 index efd7823..0000000 --- a/pi-config/reset_arduino.sh +++ /dev/null @@ -1,8 +0,0 @@ -#!/bin/bash -cd /sys/class/gpio/ -echo 6 > export -echo out > gpio6/direction -echo 0 > gpio6/value -echo 1 > gpio6/value -echo 6 > unexport - diff --git a/reset_eeprom/.gitignore b/reset_eeprom/.gitignore deleted file mode 100644 index 89cc49c..0000000 --- a/reset_eeprom/.gitignore +++ /dev/null @@ -1,5 +0,0 @@ -.pio -.vscode/.browse.c_cpp.db* -.vscode/c_cpp_properties.json -.vscode/launch.json -.vscode/ipch diff --git a/reset_eeprom/.vscode/extensions.json b/reset_eeprom/.vscode/extensions.json deleted file mode 100644 index 080e70d..0000000 --- a/reset_eeprom/.vscode/extensions.json +++ /dev/null @@ -1,10 +0,0 @@ -{ - // See http://go.microsoft.com/fwlink/?LinkId=827846 - // for the documentation about the extensions.json format - "recommendations": [ - "platformio.platformio-ide" - ], - "unwantedRecommendations": [ - "ms-vscode.cpptools-extension-pack" - ] -} diff --git a/reset_eeprom/include/README b/reset_eeprom/include/README deleted file mode 100644 index 45496b1..0000000 --- a/reset_eeprom/include/README +++ /dev/null @@ -1,39 +0,0 @@ - -This directory is intended for project header files. - -A header file is a file containing C declarations and macro definitions -to be shared between several project source files. You request the use of a -header file in your project source file (C, C++, etc) located in `src` folder -by including it, with the C preprocessing directive `#include'. - -```src/main.c - -#include "header.h" - -int main (void) -{ - ... -} -``` - -Including a header file produces the same results as copying the header file -into each source file that needs it. Such copying would be time-consuming -and error-prone. With a header file, the related declarations appear -in only one place. If they need to be changed, they can be changed in one -place, and programs that include the header file will automatically use the -new version when next recompiled. The header file eliminates the labor of -finding and changing all the copies as well as the risk that a failure to -find one copy will result in inconsistencies within a program. - -In C, the usual convention is to give header files names that end with `.h'. -It is most portable to use only letters, digits, dashes, and underscores in -header file names, and at most one dot. - -Read more about using header files in official GCC documentation: - -* Include Syntax -* Include Operation -* Once-Only Headers -* Computed Includes - -https://gcc.gnu.org/onlinedocs/cpp/Header-Files.html diff --git a/reset_eeprom/lib/README b/reset_eeprom/lib/README deleted file mode 100644 index 8c9c29c..0000000 --- a/reset_eeprom/lib/README +++ /dev/null @@ -1,46 +0,0 @@ - -This directory is intended for project specific (private) libraries. -PlatformIO will compile them to static libraries and link into executable file. - -The source code of each library should be placed in a an own separate directory -("lib/your_library_name/[here are source files]"). - -For example, see a structure of the following two libraries `Foo` and `Bar`: - -|--lib -| | -| |--Bar -| | |--docs -| | |--examples -| | |--src -| | |- Bar.c -| | |- Bar.h -| | |- library.json (optional, custom build options, etc) https://docs.platformio.org/page/librarymanager/config.html -| | -| |--Foo -| | |- Foo.c -| | |- Foo.h -| | -| |- README --> THIS FILE -| -|- platformio.ini -|--src - |- main.c - -and a contents of `src/main.c`: -``` -#include -#include - -int main (void) -{ - ... -} - -``` - -PlatformIO Library Dependency Finder will find automatically dependent -libraries scanning project source files. - -More information about PlatformIO Library Dependency Finder -- https://docs.platformio.org/page/librarymanager/ldf.html diff --git a/reset_eeprom/platformio.ini b/reset_eeprom/platformio.ini deleted file mode 100644 index 176ed79..0000000 --- a/reset_eeprom/platformio.ini +++ /dev/null @@ -1,18 +0,0 @@ -; PlatformIO Project Configuration File -; -; Build options: build flags, source filter -; Upload options: custom upload port, speed and extra flags -; Library options: dependencies, extra library storages -; Advanced options: extra scripting -; -; Please visit documentation for the other options and examples -; https://docs.platformio.org/page/projectconf.html - -[env:nanoatmega328] -platform = atmelavr -board = nanoatmega328new -framework = arduino - -lib_deps = - -monitor_speed = 115200 diff --git a/reset_eeprom/src/main.cpp b/reset_eeprom/src/main.cpp deleted file mode 100644 index 1f74652..0000000 --- a/reset_eeprom/src/main.cpp +++ /dev/null @@ -1,78 +0,0 @@ -/* - * EEPROM Clear - * - * Sets all of the bytes of the EEPROM to 0. - * Please see eeprom_iteration for a more in depth - * look at how to traverse the EEPROM. - * - * This example code is in the public domain. - */ - -#include "Arduino.h" -//#include -#include "Wire.h" - -#define EEPROMDEVICEADDRESS 0x50 -#define EEPROMSIZE 2048 - - -void writeEEPROM(unsigned int eeaddress, byte data ) -{ - Wire.beginTransmission(EEPROMDEVICEADDRESS); - Wire.write((int)(eeaddress >> 8)); // MSB - Wire.write((int)(eeaddress & 0xFF)); // LSB - Wire.write(data); - Wire.endTransmission(); - - delay(5); -} - -byte readEEPROM(unsigned int eeaddress ) -{ - byte rdata = 0xFF; - - Wire.beginTransmission(EEPROMDEVICEADDRESS); - Wire.write((int)(eeaddress >> 8)); // MSB - Wire.write((int)(eeaddress & 0xFF)); // LSB - Wire.endTransmission(); - - Wire.requestFrom(EEPROMDEVICEADDRESS,1); - - if (Wire.available()) rdata = Wire.read(); - - return rdata; -} - -void setup() { - // initialize the LED pin as an output. - pinMode(13, OUTPUT); - Serial.begin(115200); - - /*** - Iterate through each byte of the EEPROM storage. - Larger AVR processors have larger EEPROM sizes, E.g: - - Arduino Duemilanove: 512 B EEPROM storage. - - Arduino Uno: 1 kB EEPROM storage. - - Arduino Mega: 4 kB EEPROM storage. - Rather than hard-coding the length, you should use the pre-provided length function. - This will make your code portable to all AVR processors. - ***/ - - delay(1000); - Serial.println("BEGIN"); - - for (int i = 0 ; i < EEPROMSIZE ; i++) { - // writeEEPROM(i, 0xFF); - Serial.print(readEEPROM(i),HEX); - } - - // turn the LED on when we're done - digitalWrite(13, HIGH); - - Serial.println(""); - Serial.println("END"); -} - -void loop() { - /** Empty loop. **/ -} \ No newline at end of file diff --git a/reset_eeprom/test/README b/reset_eeprom/test/README deleted file mode 100644 index e7d1588..0000000 --- a/reset_eeprom/test/README +++ /dev/null @@ -1,11 +0,0 @@ - -This directory is intended for PlatformIO Unit Testing and project tests. - -Unit Testing is a software testing method by which individual units of -source code, sets of one or more MCU program modules together with associated -control data, usage procedures, and operating procedures, are tested to -determine whether they are fit for use. Unit testing finds problems early -in the development cycle. - -More information about PlatformIO Unit Testing: -- https://docs.platformio.org/page/plus/unit-testing.html