├── hardware ├── arduino │ └── zuno │ │ ├── variants │ │ └── standard │ │ │ └── pins_arduino.h │ │ ├── cores │ │ └── zuno │ │ │ ├── c_lib_minimal.h │ │ │ ├── HLCore.h │ │ │ ├── ZUNO_call_proto.h │ │ │ ├── HardwareSerial.h │ │ │ ├── ArduinoCAPI.h │ │ │ ├── EEPROM.h │ │ │ ├── ArduinoTypes.h │ │ │ ├── Arduino.h │ │ │ ├── main.c │ │ │ ├── Print.h │ │ │ ├── EEPROM.cpp │ │ │ ├── HardwareSerial.cpp │ │ │ ├── Wire.h │ │ │ ├── SPI.h │ │ │ ├── stdio.h │ │ │ ├── LLCore_arduino.h │ │ │ ├── math.h │ │ │ ├── SPI.cpp │ │ │ ├── HLCore.cpp │ │ │ ├── string.h │ │ │ ├── Stream.h │ │ │ ├── Wire.cpp │ │ │ ├── IRController.h │ │ │ ├── Print.cpp │ │ │ └── Stream.cpp │ │ ├── programmers.txt │ │ ├── libraries │ │ ├── ZUNO_MCP23017 │ │ │ ├── library.properties │ │ │ ├── keywords.txt │ │ │ ├── README.txt │ │ │ ├── license.txt │ │ │ ├── ZUNO_MCP23017.h │ │ │ └── ZUNO_MCP23017.cpp │ │ ├── ZUNO_OneWire │ │ │ └── ZUNO_OneWire.h │ │ ├── ZUNO_MCP4725 │ │ │ ├── ZUNO_MCP4725.h │ │ │ └── ZUNO_MCP4725.cpp │ │ ├── ZUNO_DS18B20 │ │ │ ├── ZUNO_DS18B20.h │ │ │ └── ZUNO_DS18B20.cpp │ │ ├── ZUNO_DHTlib │ │ │ ├── ZUNO_DHT.h │ │ │ └── ZUNO_DHT.cpp │ │ ├── ZMEKeypad │ │ │ ├── ZMEKeypad.h │ │ │ └── ZMEKeypad.cpp │ │ ├── ZUNO_BH1750 │ │ │ ├── ZUNO_BH1750.cpp │ │ │ └── ZUNO_BH1750.h │ │ ├── ZUNO_BMP180 │ │ │ ├── ZUNO_BMP180.h │ │ │ └── ZUNO_BMP180.cpp │ │ ├── ZUNO_OLED_I2C │ │ │ ├── ZUNO_OLED_I2C.h │ │ │ └── ZUNO_OLED_I2C.cpp │ │ └── ZUNO_DallasRTC │ │ │ └── ZUNO_DS3232RTC.h │ │ ├── boards.txt │ │ └── platform.txt └── examples │ ├── SimpleBlink │ └── SimpleBlink.ino │ ├── SimpleButton │ └── SimpleButton.ino │ ├── MCP23017_toggle │ └── MCP23017_toggle.ino │ ├── dht22_test │ └── dht22_test.ino │ ├── MCP23017_button │ └── MCP23017_button.ino │ ├── MCP4725_sample │ └── MCP4725_sample.ino │ ├── MCP23017_I2CTest │ └── MCP23017_I2CTest.ino │ ├── BH1750LightSensor │ └── BH1750LightSensor.ino │ ├── ControlRelay │ └── ControlRelay.ino │ ├── SimpleSwitch │ └── SimpleSwitch.ino │ ├── SimpleMultiSensor │ └── SimpleMultiSensor.ino │ ├── DS18B20Scanner │ └── DS18B20Scanner.ino │ ├── RadioBlink │ └── RadioBlink.ino │ ├── SimpleDimmer │ └── SimpleDimmer.ino │ ├── Keypad4x4 │ └── Keypad4x4.ino │ ├── SimpleBinarySensor │ └── SimpleBinarySensor.ino │ ├── StackTest │ └── StackTest.ino │ ├── MotionSensor │ └── MotionSensor.ino │ ├── BMP180Test │ └── BMP180Test.ino │ ├── IRScanner │ └── IRScanner.ino │ ├── IR2ZWave │ └── IR2ZWave.ino │ ├── WaterMeter │ └── WaterMeter.ino │ ├── ZWave2IR │ └── ZWave2IR.ino │ └── Certified10Channels │ └── Certified10Channels.ino ├── ISSUE_TEMPLATE.md └── README.md /hardware/arduino/zuno/variants/standard/pins_arduino.h: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/c_lib_minimal.h: -------------------------------------------------------------------------------- 1 | #include "ArduinoTypes.h" 2 | #define strlen(str) zme_strlen(str) 3 | BYTE zme_strlen(char * str); 4 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/programmers.txt: -------------------------------------------------------------------------------- 1 | zprog.name=Z-Uno Programmer 2 | zprog.communication=usb 3 | zprog.protocol=usb 4 | zprog.program.protocol=usb 5 | zprog.program.tool=zprog 6 | zprog.program.extra_params=prog -d {serial.port} -f "{build.path}/{build.project_name}.ihex" 7 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/HLCore.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | 4 | DWORD pulseIn(s_pin pin, byte level, DWORD timeout); 5 | long map(long x, long in_min, long in_max, long out_min, long out_max); 6 | 7 | void delayMicroseconds(word us); 8 | 9 | 10 | //void testZunoCall(); -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/ZUNO_call_proto.h: -------------------------------------------------------------------------------- 1 | // Здесь только то, что действительно нужно из CoreArduino. 2 | BYTE zunoPopByte(void); 3 | WORD zunoPopWord(void); 4 | DWORD zunoPopDWORD(void); 5 | void zunoPushByte(BYTE value); 6 | void zunoPushWord(WORD value); 7 | void zunoPushDword(DWORD value); 8 | void zunoCall(void); 9 | WORD reinterpPOINTER(byte * ptr); 10 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_MCP23017/library.properties: -------------------------------------------------------------------------------- 1 | name=Adafruit MCP23017 Arduino Library 2 | version=1.0.1 3 | author=Adafruit 4 | maintainer=Adafruit 5 | sentence=Library for the MCP23017 I2C Port Expander 6 | paragraph=Library for the MCP23017 I2C Port Expander 7 | category=Signal Input/Output 8 | url=https://github.com/adafruit/Adafruit-MCP23017-Arduino-Library 9 | architectures=* 10 | -------------------------------------------------------------------------------- /hardware/examples/SimpleBlink/SimpleBlink.ino: -------------------------------------------------------------------------------- 1 | /* 2 | * That is a Simple Blink Sketch. It just blinks the LED 3 | */ 4 | 5 | // LED pin number 6 | #define LED_PIN 13 7 | 8 | void setup() { 9 | pinMode(LED_PIN, OUTPUT); // set LED pin as output 10 | } 11 | 12 | void loop() { 13 | digitalWrite(LED_PIN, HIGH); // turn LED on 14 | delay(1000); // wait for 1 second 15 | digitalWrite(LED_PIN, LOW); // turn LED off 16 | delay(1000); // wait for 1 second 17 | } 18 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_MCP23017/keywords.txt: -------------------------------------------------------------------------------- 1 | ####################################### 2 | # Syntax Coloring Map for MCP23017 3 | ####################################### 4 | 5 | ####################################### 6 | # Datatypes (KEYWORD1) 7 | ####################################### 8 | 9 | MCP23017 KEYWORD1 10 | 11 | ####################################### 12 | # Methods and Functions (KEYWORD2) 13 | ####################################### 14 | 15 | pullUp KEYWORD2 16 | writeGPIOAB KEYWORD2 17 | readGPIOAB KEYWORD2 18 | 19 | ####################################### 20 | # Constants (LITERAL1) 21 | ####################################### 22 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_OneWire/ZUNO_OneWire.h: -------------------------------------------------------------------------------- 1 | #ifndef ZUNO_ONEWIRE_LIB 2 | #define ZUNO_ONEWIRE_LIB 3 | 4 | #include "Arduino.h" 5 | class OneWire 6 | { 7 | public: 8 | OneWire(s_pin bus_pin); 9 | 10 | byte reset(void); 11 | void write(byte v, byte power = 1); 12 | byte read(); 13 | void select(byte * rom); 14 | void skip(); 15 | void depower(); 16 | void readROM(byte * rom); 17 | byte crc8(byte *addr, byte len); 18 | 19 | void reset_search(); 20 | bool search(uint8_t *newAddr); 21 | 22 | 23 | 24 | private: 25 | s_pin bus_pin; 26 | 27 | byte LastDiscrepancy; 28 | byte LastFamilyDiscrepancy; 29 | bool LastDeviceFlag; 30 | 31 | bool read_bit(); 32 | void write_bit(bool bit); 33 | 34 | 35 | }; 36 | 37 | #endif /// ZUNO_ONEWIRE_LIB -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/HardwareSerial.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include "Stream.h" 4 | 5 | class HardwareSerial: public Stream 6 | { 7 | private: 8 | BYTE func_vec; 9 | 10 | public: 11 | 12 | HardwareSerial(BYTE bfn); // bfn = like ZUNO_FUNC_SERIAL1_BEGIN 13 | 14 | void begin(); 15 | void begin(DWORD baud); 16 | void end(); 17 | virtual int available(void); 18 | virtual int peek(void); 19 | virtual int read(void); 20 | 21 | virtual void flush(void); 22 | virtual size_t write(uint8_t); 23 | 24 | size_t write(unsigned long n) { return write((uint8_t)n); } 25 | size_t write(long n) { return write((uint8_t)n); } 26 | size_t write(unsigned int n) { return write((uint8_t)n); } 27 | size_t write(int n) { return write((uint8_t)n); } 28 | 29 | 30 | }; 31 | 32 | extern HardwareSerial Serial; 33 | extern HardwareSerial Serial1; 34 | extern HardwareSerial Serial0; 35 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_MCP23017/README.txt: -------------------------------------------------------------------------------- 1 | This is a library for the MCP23017 I2c Port Expander 2 | 3 | These chips use I2C to communicate, 2 pins required to interface 4 | 5 | Adafruit invests time and resources providing this open source code, 6 | please support Adafruit and open-source hardware by purchasing 7 | products from Adafruit! 8 | 9 | Written by Limor Fried/Ladyada for Adafruit Industries. 10 | BSD license, check license.txt for more information 11 | All text above must be included in any redistribution 12 | 13 | To download. click the DOWNLOADS button in the top right corner, rename the uncompressed folder Adafruit_MCP23017. Check that the Adafruit_MCP23017 folder contains Adafruit_MCP23017.cpp and Adafruit_MCP23017.h 14 | 15 | Place the Adafruit_MCP23017 library folder your /libraries/ folder. You may need to create the libraries subfolder if its your first library. Restart the IDE. -------------------------------------------------------------------------------- /hardware/examples/SimpleButton/SimpleButton.ino: -------------------------------------------------------------------------------- 1 | /* 2 | * That is a Simple button example 3 | * Z-Uno has a built in service button, 4 | * used to include/exclude the device, 5 | * reset it and of course 6 | * is usable for you. 7 | * In this example we track the button, 8 | * once it's pressed we shine the built in LED 9 | */ 10 | // button pin number 11 | #define BTN_PIN 18 12 | // built in LED number 13 | #define LED_PIN 13 14 | 15 | void setup() { 16 | pinMode(LED_PIN, OUTPUT); // set LED pin as output 17 | pinMode(BTN_PIN, INPUT_PULLUP); // set button pin as Input 18 | } 19 | 20 | void loop() { 21 | // sample button state 22 | byte buttonState = digitalRead(BTN_PIN); 23 | 24 | if (buttonState == HIGH) { // if button is not pressed 25 | digitalWrite(LED_PIN, LOW); // turn the LED off 26 | } else { // if button is pressed 27 | digitalWrite(LED_PIN, HIGH); // turn the LED on 28 | } 29 | } 30 | 31 | -------------------------------------------------------------------------------- /hardware/examples/MCP23017_toggle/MCP23017_toggle.ino: -------------------------------------------------------------------------------- 1 | #include 2 | #include "ZUNO_MCP23017.h" 3 | 4 | // Basic pin reading and pullup test for the MCP23017 I/O expander 5 | // public domain! 6 | 7 | // Connect SCL to i2c clock - on Z-Uno thats Digital 9 8 | // Connect SDA to i2c data - on Z-Uno thats Digital 10 9 | // Connect pins #15, 16 and 17 of the expander to ground (address selection) 10 | // Connect pin #9 of the expander to 5V (power) 11 | // Connect pin #10 of the expander to ground (common ground) 12 | // Connect pin #18 through a ~10kohm resistor to 5V (reset pin, active low) 13 | 14 | // Output #0 is on pin 21 so connect an LED or whatever from that to ground 15 | 16 | ZUNO_MCP23017 mcp; 17 | 18 | void setup() { 19 | mcp.begin(); // use default address 0 20 | 21 | mcp.pinMode(0, OUTPUT); 22 | } 23 | 24 | 25 | // flip the pin #0 up and down 26 | 27 | void loop() { 28 | delay(100); 29 | 30 | mcp.digitalWrite(0, HIGH); 31 | 32 | delay(100); 33 | 34 | mcp.digitalWrite(0, LOW); 35 | } -------------------------------------------------------------------------------- /hardware/examples/dht22_test/dht22_test.ino: -------------------------------------------------------------------------------- 1 | #include "ZUNO_DHT.h" 2 | 3 | 4 | DHT dht22_sensor(11, DHT22); 5 | 6 | void setup() { 7 | 8 | Serial.begin(115200); 9 | dht22_sensor.begin(); 10 | 11 | Serial.println("\n **** Sketch is starting... ****\n"); 12 | 13 | 14 | } 15 | 16 | 17 | 18 | 19 | void loop() { 20 | 21 | byte result; 22 | byte i; 23 | byte raw_data[5]; 24 | 25 | Serial.print("Millis:"); 26 | Serial.println(millis()); 27 | 28 | 29 | result = dht22_sensor.read(true); 30 | Serial.print("DHT read result:"); 31 | Serial.println(result); 32 | 33 | Serial.print("Raw data: { "); 34 | dht22_sensor.getRawData(raw_data); 35 | for(i=0;i<5;i++) 36 | { 37 | Serial.print(raw_data[i], HEX); 38 | Serial.print(" "); 39 | } 40 | Serial.println("} "); 41 | 42 | Serial.print("Temperature:"); 43 | Serial.println(dht22_sensor.readTemperature()); 44 | Serial.print("Humidity:"); 45 | Serial.println(dht22_sensor.readHumidity()); 46 | 47 | delay(3000); 48 | 49 | 50 | 51 | } 52 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/ArduinoCAPI.h: -------------------------------------------------------------------------------- 1 | #ifndef ARDUINO_ZUNO_C_API 2 | #define ARDUINO_ZUNO_C_API 3 | 4 | #include "ArduinoTypes.h" 5 | // Интерфейс низкого уровня, который доступен пользователю 6 | // Прототипы из LLCore_arduino.c 7 | void pinMode(BYTE pin, BYTE mode); 8 | BYTE digitalRead(BYTE pin); 9 | void digitalWrite(BYTE pin, BYTE value); 10 | void delay(DWORD value); 11 | WORD analogRead(BYTE pin); 12 | void analogWrite(BYTE pin, BYTE value); 13 | DWORD millis(); 14 | 15 | // WakeUp on KS 16 | void zunoSetupKeyScannerWU(byte cols_num); 17 | // Z-Uno Systems calls 18 | void zunoSendUncolicitedReport(BYTE channel,WORD value); 19 | void zunoSendAssociationCommand(BYTE group, BYTE assoc_type, BYTE param1, BYTE param2); 20 | void zunoSendDeviceToSleep(void); 21 | BYTE zunoGetWakeReason(void); 22 | 23 | void delayLoops(byte v); 24 | void NOPS(byte i); 25 | 26 | // interrupts 27 | void noInterrupts(); 28 | void interrupts(); 29 | 30 | // math 31 | long map(long x, long in_min, long in_max, long out_min, long out_max); 32 | 33 | 34 | 35 | 36 | #endif // ARDUINO_ZUNO_C_API 37 | -------------------------------------------------------------------------------- /hardware/examples/MCP23017_button/MCP23017_button.ino: -------------------------------------------------------------------------------- 1 | #include 2 | #include "ZUNO_MCP23017.h" 3 | 4 | // Basic pin reading and pullup test for the MCP23017 I/O expander 5 | // public domain! 6 | 7 | // Connect SCL to i2c clock - on Z-Uno thats Digital 9 8 | // Connect SDA to i2c data - on Z-Uno thats Digital 10 9 | // Connect pins #15, 16 and 17 of the expander to ground (address selection) 10 | // Connect pin #9 of the expander to 5V (power) 11 | // Connect pin #10 of the expander to ground (common ground) 12 | // Connect pin #18 through a ~10kohm resistor to 5V (reset pin, active low) 13 | 14 | // Input #0 is on pin 21 so connect a button or switch from there to ground 15 | 16 | ZUNO_MCP23017 mcp; 17 | 18 | void setup() { 19 | mcp.begin(); // use default address 0 20 | 21 | mcp.pinMode(0, INPUT); 22 | mcp.pullUp(0, HIGH); // turn on a 100K pullup internally 23 | 24 | pinMode(13, OUTPUT); // use the p13 LED as debugging 25 | } 26 | 27 | 28 | 29 | void loop() { 30 | // The LED will 'echo' the button 31 | digitalWrite(13, mcp.digitalRead(0)); 32 | } -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/EEPROM.h: -------------------------------------------------------------------------------- 1 | #ifndef ZUNO_EEPROM_LIBRARY 2 | #define ZUNO_EEPROM_LIBRARY 3 | 4 | #include "ArduinoTypes.h" 5 | #include "ZUNO_Definitions.h" 6 | 7 | class EEPROMClass 8 | { 9 | public: 10 | EEPROMClass(byte read_func):rfunc(read_func){}; 11 | 12 | 13 | word put(DWORD address, void * value, word val_size); 14 | word get(DWORD address, void * value, word val_size); 15 | byte read(DWORD address); 16 | void update(DWORD address, byte value); 17 | void write(DWORD address, byte value); 18 | 19 | private: 20 | byte temp_byte; 21 | byte rfunc; 22 | 23 | 24 | }; 25 | class NZRAMClass 26 | { 27 | public: 28 | NZRAMClass(byte read_func):rfunc(read_func){}; 29 | 30 | byte put(byte address, void * value, byte val_size); 31 | byte get(byte address, void * value, byte val_size); 32 | byte read(byte address); 33 | void update(byte address, byte value); 34 | void write(byte address, byte value); 35 | 36 | private: 37 | 38 | byte temp_byte; 39 | byte rfunc; 40 | 41 | }; 42 | extern EEPROMClass EEPROM; 43 | extern NZRAMClass NZRAM; 44 | 45 | #endif // ZUNO_EEPROM_LIBRARY -------------------------------------------------------------------------------- /hardware/examples/MCP4725_sample/MCP4725_sample.ino: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | #define voltInput A0 5 | 6 | ZUNO_MCP4725 dac; // constructor 7 | 8 | void setup(void) { 9 | Serial.begin(0); 10 | dac.begin(0x60); // The I2C Address: Run the I2C Scanner if you're not sure 11 | 12 | } 13 | 14 | void loop(void) { 15 | 16 | uint32_t dac_val; 17 | int raw_adcRead = 0; 18 | float voltRead = 0; 19 | 20 | float calculated_output; 21 | 22 | 23 | for (dac_val = 0; dac_val < 4096; dac_val = dac_val + 15) 24 | { 25 | calculated_output = (5.0/4096.0) * dac_val; 26 | dac.setVoltage(dac_val, false); 27 | delay(250); 28 | raw_adcRead = analogRead(voltInput); 29 | voltRead = (raw_adcRead * 5.0 )/ 1024.0; 30 | 31 | Serial.print("MCP4725 DAC Value: "); 32 | Serial.print(dac_val); 33 | 34 | Serial.print("\tCalculated Voltage: "); 35 | Serial.print(calculated_output,3); 36 | 37 | Serial.print("\tADC Value (Z-Uno input): "); 38 | Serial.print(raw_adcRead); 39 | 40 | Serial.print("\tZ-Uno Voltage: "); 41 | Serial.println(voltRead,3); 42 | } 43 | } 44 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_MCP4725/ZUNO_MCP4725.h: -------------------------------------------------------------------------------- 1 | /**************************************************************************/ 2 | /*! 3 | @file Adafruit_MCP4725.h 4 | @author K. Townsend (Adafruit Industries) 5 | @license BSD (see license.txt) 6 | 7 | This is a library for the Adafruit MCP4725 breakout board 8 | ----> http://www.adafruit.com/products/935 9 | 10 | Adafruit invests time and resources providing this open source code, 11 | please support Adafruit and open-source hardware by purchasing 12 | products from Adafruit! 13 | 14 | @section HISTORY 15 | 16 | v1.0 - First release 17 | some changes for Z-Uno by m.p. 22.11.2016 18 | @file ZUNO_MCP4725.h 19 | 20 | */ 21 | /**************************************************************************/ 22 | 23 | #include 24 | 25 | #define MCP4726_CMD_WRITEDAC (0x40) // Writes data to the DAC 26 | #define MCP4726_CMD_WRITEDACEEPROM (0x60) // Writes data to the DAC and the EEPROM (persisting the assigned value after reset) 27 | 28 | class ZUNO_MCP4725{ 29 | public: 30 | ZUNO_MCP4725(); 31 | void begin(uint8_t a); 32 | void setVoltage( uint16_t output, bool writeEEPROM ); 33 | 34 | private: 35 | uint8_t _i2caddr; 36 | }; 37 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/ArduinoTypes.h: -------------------------------------------------------------------------------- 1 | #ifndef ARDUINO_LIKE_TYPES__ 2 | #define ARDUINO_LIKE_TYPES__ 3 | #include "ZUNO_Definitions.h" 4 | 5 | typedef unsigned char boolean; 6 | typedef unsigned char uint8_t; 7 | typedef unsigned char s_pin; 8 | typedef unsigned short uint16_t; 9 | typedef unsigned long uint32_t; 10 | 11 | typedef char int8_t; 12 | typedef short int16_t; 13 | typedef long int32_t; 14 | 15 | 16 | typedef unsigned short size_t; 17 | typedef unsigned char BYTE; 18 | typedef unsigned short WORD; 19 | typedef unsigned long DWORD; 20 | 21 | #define byte BYTE 22 | #define word WORD 23 | #define bool BYTE 24 | 25 | #define TRUE 1 26 | #define FALSE 0 27 | 28 | typedef unsigned long time_t; 29 | 30 | struct tmElements_s { 31 | uint8_t Second; 32 | uint8_t Minute; 33 | uint8_t Hour; 34 | uint8_t Wday; // day of week, sunday is day 1 35 | uint8_t Day; 36 | uint8_t Month; 37 | uint8_t Year; // offset from 1970; 38 | }; 39 | 40 | 41 | typedef struct tmElements_s tmElements_t; 42 | typedef enum tmElementsFields{ 43 | tmSecond, tmMinute, tmHour, tmWday, tmDay,tmMonth, tmYear, tmNbrFields 44 | }tmElementsFields_t; 45 | 46 | //#define true TRUE 47 | //#define false FALSE 48 | 49 | 50 | #endif // ARDUINO_LIKE_TYPES__ -------------------------------------------------------------------------------- /ISSUE_TEMPLATE.md: -------------------------------------------------------------------------------- 1 | _Please fill your bug report here_ 2 | 3 | **More info:** 4 | - **Z-Uno bootloader version:** 2.1.x (release version or test-ucxx?) 5 | - **Security:** none/S2/S0 6 | - **Frequency:** EU/US/RU/ANZ-BR/IN/CN/JP/KR/TW 7 | - **Device included:** yes/no 8 | - **Device included securely by controller:** yes/no 9 | - **Controller:** RaZberry/Z-Way/Fibaro HC2/Fibaro HCL/Vera/other 10 | 11 | **Connected peripherals:** 12 | _Please add here a description, photo and/or schematics of your peripherals_ 13 | 14 | **Code:** 15 | _If you can minimize your code to still reproduce the bug, please do it before reporting_ 16 | ```C 17 | your code here 18 | ``` 19 | 20 | **Compiler log:** 21 | _Please paster the compiler output_ 22 | ``` 23 | ---------------------------------------------------------- 24 | FIRMWARE DATA 25 | ---------------------------------------------------------- 26 | REVISION:02.15 27 | Z-WAVE FREQUENCY:RU 28 | 29 | ... (more lines up to) 30 | 31 | CHIP:1546 REVISION:4 32 | ``` 33 | 34 | **Debug output:** 35 | _Connect to UART0, enable Logging->UART0, open logging monitor and dump the output. Should look like:_ 36 | ``` 37 | 0000:00 03 38 | 0000:00 00 39 | 0010:A0 00 40 | 0011:A0 00 41 | 0012:A0 00 42 | ``` 43 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/Arduino.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | #include "ArduinoTypes.h" 3 | #include "ZUNO_Definitions.h" 4 | // Здесь добавляются все библиотеки для которых необходимы плюсы... 5 | #include "HardwareSerial.h" // Поддержка Serial 6 | // Все обычные С-функции 7 | #include "ArduinoCAPI.h" 8 | #include "HLCore.h" 9 | 10 | // Хидеры SDCC 11 | #include "math.h" 12 | 13 | 14 | 15 | // В SDCC все math-функции только float 16 | // Преобразуем к привычным прототипам 17 | #define sin(x) sinf(x) 18 | #define cos(x) cosf(x) 19 | #define tan(x) tanf(x) 20 | #define cot(x) cotf(x) 21 | #define asin(x) asinf(x) 22 | #define acos(x) acosf(x) 23 | #define atan(x) atanf(x) 24 | #define atan2(x, y) atan2f(x, y) 25 | #define sinh(x) sinhf(x) 26 | #define cosh(x) coshf(x) 27 | #define tanh(x) tanhf(x) 28 | #define exp(x) expf(x) 29 | #define log(x) logf(x) 30 | #define log10(x) log10f(x) 31 | #define pow(x,y) powf(x,y) 32 | #define sqrt(x) sqrtf(x) 33 | #define fabs(x) fabsf(x) 34 | #define ceil(x) ceilf(x) 35 | #define floor(x) floorf(x) 36 | #define modf(x,y) modff(x,y) 37 | #define frexp(x, pw2) frexpf(x, pw2) 38 | #define ldexp(x, pw2) ldexpf(x, pw2) 39 | 40 | 41 | 42 | 43 | //********************************************** 44 | void setup(void); 45 | void loop(void); 46 | 47 | 48 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/main.c: -------------------------------------------------------------------------------- 1 | #include "LLCore_arduino.h" 2 | #pragma codeseg BANK3 3 | #pragma preproc_asm + 4 | __code __at (0x8000) char lookupString[] = "LOOK UP ARDUINO HEX CODE"; 5 | 6 | 7 | void InitArduinoEnvironment(void); 8 | void setup(); 9 | void loop(); 10 | 11 | 12 | //__sfr __at (0x81) SP; 13 | 14 | 15 | 16 | // These functions will return to relative positions determined by the linker. 17 | void main(void) { 18 | InitArduinoEnvironment(); 19 | 20 | for (;;) { 21 | loop(); 22 | } 23 | } 24 | 25 | void xdata8051_init(void) { 26 | __asm 27 | ; 28 | ; check there is any user xdata 29 | MOV r0,#l_XINIT 30 | MOV a,r0 31 | ORL a,#(l_XINIT >> 8) 32 | JZ EXIT 33 | ; 34 | ; 35 | ; 36 | ; load registers 37 | ; r0-1 38 | MOV r1,#((l_XINIT+255) >> 8) 39 | MOV r2,#s_XINIT 40 | MOV r3,#(s_XINIT >> 8) 41 | MOV r4,#s_XISEG 42 | MOV r5,#(s_XISEG >> 8) 43 | CYCLE: clr a 44 | MOV dpl,r2 45 | MOV dph,r3 46 | MOVc a,@a+dptr 47 | INC dptr 48 | MOV r2, dpl 49 | MOV r3, dph 50 | MOV dpl,r4 51 | MOV dph,r5 52 | MOVX @dptr,a 53 | INC dptr 54 | MOV r4,dpl 55 | MOV r5,dph 56 | DJNZ r0,CYCLE 57 | DJNZ r1,CYCLE 58 | EXIT: 59 | __endasm; 60 | } 61 | 62 | void InitArduinoEnvironment(void) { 63 | xdata8051_init(); 64 | setup(); 65 | } 66 | 67 | 68 | 69 | 70 | -------------------------------------------------------------------------------- /hardware/examples/MCP23017_I2CTest/MCP23017_I2CTest.ino: -------------------------------------------------------------------------------- 1 | /* 2 | * Тестирование шины I2C с помощью распостраненного порт-экстендера MCP23017 3 | * Есть 2-ва идентичных варианта кода: На C++ и без его использования 4 | * Пины порт-экстендера: 5 | * 15,16,17 -> GND (Адрес == 0) 6 | * 18 -> 3v3 (Reset подтянут) 7 | * 10 -> GND (Питание) 8 | * 9 -> 3v3 (Питание) 9 | * 12 -> ZUNO(9) SCL 10 | * 13 -> ZUNO(10) SDA 11 | */ 12 | #include "Wire.h" 13 | 14 | 15 | void setup() 16 | { 17 | 18 | 19 | // CXX version 20 | Wire.begin(); // wake up I2C bus 21 | // set I/O pins to outputs 22 | Wire.beginTransmission(0x20); 23 | Wire.write(0x00); // IODIRA register 24 | Wire.write(0x00); // set all of port A to outputs 25 | Wire.endTransmission(); 26 | 27 | 28 | Serial.begin(); 29 | 30 | 31 | } 32 | 33 | void loop() 34 | { 35 | 36 | Serial.print("Loop millis: "); 37 | Serial.println(millis()); 38 | 39 | 40 | 41 | // CXX version 42 | Wire.beginTransmission(0x20); 43 | Wire.write(0x12); // address bank A 44 | Wire.write((byte)0xAA); // value to send - all HIGH 45 | Wire.endTransmission(); 46 | delay(500); 47 | Wire.beginTransmission(0x20); 48 | Wire.write(0x12); // address bank A 49 | Wire.write((byte)0x55); // value to send - all HIGH 50 | Wire.endTransmission(); 51 | delay(500); 52 | 53 | 54 | 55 | 56 | } -------------------------------------------------------------------------------- /hardware/examples/BH1750LightSensor/BH1750LightSensor.ino: -------------------------------------------------------------------------------- 1 | // demo sketch for connecting I2C light sensor BH1750 to Z-Uno using ZUNO_BH1750 library 2 | 3 | #include "ZUNO_BH1750.h" 4 | #define DEBUG 5 | 6 | BH1750 bh1750; 7 | 8 | // BH1750 address on the bus: BH1750_I2CADDR_L = 0x23 9 | #define BH1750_I2CADDR BH1750_I2CADDR_L 10 | 11 | word lightLux; 12 | 13 | // set up channel 14 | ZUNO_SETUP_CHANNELS( 15 | ZUNO_SENSOR_MULTILEVEL(ZUNO_SENSOR_MULTILEVEL_TYPE_LUMINANCE, 16 | SENSOR_MULTILEVEL_SCALE_LUX, 17 | SENSOR_MULTILEVEL_SIZE_TWO_BYTES, 18 | SENSOR_MULTILEVEL_PRECISION_ZERO_DECIMALS, 19 | getterLight) 20 | ); 21 | 22 | void setup() { 23 | #ifdef DEBUG 24 | Serial.begin(); 25 | #endif 26 | 27 | // Start continous measurement in HIGH_RES_MODE at 1 lx resolution 28 | // Measurement time is approx 120ms. max time 180ms defined as BH1750_HIGH_RES_MODE_MAXTIME 29 | bh1750.begin(BH1750_CONTINUOUS_HIGH_RES_MODE, BH1750_I2CADDR); 30 | 31 | #ifdef DEBUG 32 | Serial.println("start"); 33 | #endif 34 | } 35 | 36 | void loop() { 37 | lightLux = bh1750.readLightLevel(BH1750_I2CADDR); 38 | 39 | #ifdef DEBUG 40 | Serial.print("light = "); 41 | Serial.println(lightLux); 42 | #endif 43 | zunoSendReport(1); 44 | // send every 30 sec 45 | delay(30000); 46 | } 47 | 48 | word getterLight() { 49 | return lightLux; 50 | } -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_DS18B20/ZUNO_DS18B20.h: -------------------------------------------------------------------------------- 1 | #ifndef DALLAS_DS_18B20LIB 2 | #define DALLAS_DS_18B20LIB 3 | #include "Arduino.h" 4 | #include "ZUNO_OneWire.h" 5 | 6 | #define BAD_TEMP -32767 7 | 8 | enum 9 | { 10 | DS18B20_RESOLUTION_9BIT = 0, 11 | DS18B20_RESOLUTION_10BIT, 12 | DS18B20_RESOLUTION_11BIT, 13 | DS18B20_RESOLUTION_12BIT 14 | 15 | 16 | }; 17 | class DS18B20Sensor 18 | { 19 | public: 20 | DS18B20Sensor(OneWire * ow); 21 | 22 | // Search for all DS18B20 sensors connected to 1Wire bus. 23 | // Copies found sensor's addresses (ROM) to buffer 24 | // one by one 25 | // Returns: 26 | // number of found sensors 27 | 28 | byte findAllSensors(byte * rom); 29 | 30 | // Search for alone sensor. 31 | // Copies found sensor's address (ROM) to buffer 32 | // Works faster for 1 sensor cases 33 | // Returns: 34 | // 1 if we have a valid sensor connected 35 | // 0 otherwise 36 | byte scanAloneSensor(byte * rom); 37 | 38 | void setResolution(byte res, byte * addr = NULL); 39 | byte getResolution(){return current_resolution;}; 40 | 41 | // Return temperarure in cents of Celsius 42 | // sonsume less memory of sketch than getTemperature() 43 | int getTempC100(byte * addr = NULL); 44 | // Returns temperature as float in Celsius 45 | float getTemperature(byte * addr = NULL); 46 | 47 | 48 | 49 | private: 50 | OneWire * my_ow; 51 | byte current_resolution; 52 | byte current_delay; 53 | 54 | }; 55 | 56 | #endif // DALLAS_DS_18B20LIB 57 | -------------------------------------------------------------------------------- /hardware/examples/ControlRelay/ControlRelay.ino: -------------------------------------------------------------------------------- 1 | /* 2 | * This example shows basic Switch Binary functionality 3 | * Control an external relay on pin 13 4 | */ 5 | 6 | // pin number, where relay is connected 7 | #define RELAY_PIN 13 8 | 9 | // variable to store current relay state 10 | byte lastSetValue; 11 | 12 | // next macro sets up the Z-Uno channels 13 | // in this example we set up 1 switch binary channel 14 | // you can read more on http://z-uno.z-wave.me/Reference/ZUNO_SWITCH_BINARY/ 15 | ZUNO_SETUP_CHANNELS(ZUNO_SWITCH_BINARY(getter, setter)); 16 | 17 | void setup() { 18 | pinMode(RELAY_PIN, OUTPUT); // set up relay pin as output 19 | } 20 | 21 | void loop() { 22 | // loop is empty, because all the control comes over the Z-Wave 23 | } 24 | 25 | 26 | // function, which returns the previously saved relay value 27 | // this function runs only once the controller asks 28 | byte getter() { 29 | return lastSetValue; 30 | } 31 | 32 | 33 | // function, which sets new relay state 34 | // this function runs only once the controller sends new value 35 | void setter(byte newValue) { 36 | // newValue is a variable, holding a "value" 37 | // which came from the controller or other Z-Wave device 38 | if (newValue > 0) { // if greater then zero 39 | digitalWrite(RELAY_PIN, HIGH); //turn relay on 40 | } else { // if equals zero 41 | digitalWrite(RELAY_PIN, LOW); //turn relay off 42 | } 43 | 44 | // save the new value in a variable 45 | lastSetValue = newValue; 46 | } 47 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Z-Uno-Core 2 | Core files for Z-Uno support in Arduino IDE 1.6.5 3 | 4 | Arduino Board Manager is used to install these files. Installation guide: https://z-uno.z-wave.me/install 5 | 6 | Z-Uno is the first and only easy to use developer board that allows you to create your own Z-Wave device without deep knowledge of Z-Wave protocol or programming. Z-Uno is a mix of Z-Wave home automation radio protocol power and Arduino simplicity. Being inspired by Arduino project Z-Uno inherits all concepts of easy-to-use hardware and software solutions, keeping maximum flexibility. 7 | 8 | Z-Uno is a fully DIY product. It is made for those who are limited by existing choice of Z-Wave products and wants to extend their smart homes with more sensors and actuators: connect LEDs, buttons, switches, motors or any low voltage sensor including most of Arduino compatible sensors. 9 | 10 | Z-Uno programming is done by writing sketch in simplified C language (language reference: https://z-uno.z-wave.me/Reference) and loaded into Z-Uno using Arduino IDE. Many examples and comprehensive tutorials will help you to make your own project. See https://z-uno.z-wave.me/examples 11 | 12 | Being Z-Wave Plus certified device, Z-Uno is the perfect companion for you RaZberry gateway (https://razberry.z-wave.me). Z-Uno is compatible with other controllers too. 13 | 14 | # Z-Uno project roadmap 15 | Z-Uno TODO list is available here: https://gist.github.com/PoltoS/85d9bceedfa5d77ae4d2dafa6f063d55. Version in [] is the expected release to include the feature in question. 16 | -------------------------------------------------------------------------------- /hardware/examples/SimpleSwitch/SimpleSwitch.ino: -------------------------------------------------------------------------------- 1 | /* 2 | * That is a Simple Sensor Multilevel example 3 | * It measures the value on the potentiometer 4 | * And sends report to the controller if changed 5 | */ 6 | 7 | // LED pin number 8 | #define LED_PIN 13 9 | 10 | 11 | // Last saved LED value 12 | byte currentLEDValue; 13 | 14 | // next macro sets up the Z-Uno channels 15 | // in this example we set up 1 switch binary channel 16 | // you can read more on http://z-uno.z-wave.me/Reference/ZUNO_SWITCH_BINARY/ 17 | ZUNO_SETUP_CHANNELS(ZUNO_SWITCH_BINARY(getter, setter)); 18 | 19 | void setup() { 20 | pinMode(LED_PIN, OUTPUT); // setup pin as output 21 | } 22 | 23 | void loop() { 24 | // loop is empty, because all the control comes over the Z-Wave 25 | } 26 | 27 | // function, which sets new relay state 28 | // this function runs only once the controller sends new value 29 | void setter (byte value) { 30 | // value is a variable, holding a "new value" 31 | // which came from the controller or other Z-Wave device 32 | if (value > 0) { // if greater then zero 33 | digitalWrite (LED_PIN, HIGH); //turn LED on 34 | } else { // if equals zero 35 | digitalWrite(LED_PIN, LOW); //turn LED off 36 | } 37 | // let's save our value for the situation, when the controller will ask us about it 38 | currentLEDValue = value; 39 | } 40 | 41 | // function, which returns the previously saved relay value 42 | // this function runs only once the controller asks 43 | byte getter (){ 44 | return currentLEDValue; 45 | } 46 | 47 | -------------------------------------------------------------------------------- /hardware/examples/SimpleMultiSensor/SimpleMultiSensor.ino: -------------------------------------------------------------------------------- 1 | /* 2 | * That is a Simple Sensor Multilevel example 3 | * It measures the value on the potentiometer 4 | * And sends report to the controller if changed 5 | */ 6 | 7 | // LED pin number 8 | #define LED_PIN 13 9 | // Potentiometer pin number 10 | #define POT_PIN 6 11 | 12 | // channel number 13 | #define ZUNO_CHANNEL_NUMBER_ONE 1 14 | 15 | // Last saved potentiometer value 16 | byte lastValue; 17 | 18 | // next macro sets up the Z-Uno channels 19 | // in this example we set up 1 sensor multilevel channel 20 | // you can read more on http://z-uno.z-wave.me/Reference/ZUNO_SENSOR_MULTILEVEL/ 21 | ZUNO_SETUP_CHANNELS(ZUNO_SENSOR_MULTILEVEL_GENERAL_PURPOSE(getter)); 22 | 23 | void setup() { 24 | pinMode(LED_PIN, OUTPUT); // setup pin as output 25 | pinMode(POT_PIN, INPUT); //setup potentiometer pin as input 26 | } 27 | void loop() { 28 | // read potemtiometer value and save it inside a variable 29 | byte currentValue = (byte) (analogRead(A3) / 4); 30 | 31 | // if the value is different then the previously measured one 32 | // save it and send a report 33 | if (currentValue != lastValue) { 34 | // save the value 35 | lastValue = currentValue; 36 | // send report to the controller 37 | zunoSendReport(ZUNO_CHANNEL_NUMBER_ONE); 38 | } 39 | } 40 | 41 | // function, which returns the previously saved potentiometer value 42 | // this function runs only once the controller asks 43 | byte getter(void) { 44 | byte tempVariable; 45 | tempVariable = (byte)((((word) lastValue)*100)/0xff); 46 | return tempVariable; 47 | } 48 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_MCP23017/license.txt: -------------------------------------------------------------------------------- 1 | Software License Agreement (BSD License) 2 | 3 | Copyright (c) 2012, Adafruit Industries 4 | All rights reserved. 5 | 6 | Redistribution and use in source and binary forms, with or without 7 | modification, are permitted provided that the following conditions are met: 8 | 1. Redistributions of source code must retain the above copyright 9 | notice, this list of conditions and the following disclaimer. 10 | 2. Redistributions in binary form must reproduce the above copyright 11 | notice, this list of conditions and the following disclaimer in the 12 | documentation and/or other materials provided with the distribution. 13 | 3. Neither the name of the copyright holders nor the 14 | names of its contributors may be used to endorse or promote products 15 | derived from this software without specific prior written permission. 16 | 17 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS ''AS IS'' AND ANY 18 | EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 19 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 20 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY 21 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 22 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 23 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 24 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 26 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_DHTlib/ZUNO_DHT.h: -------------------------------------------------------------------------------- 1 | /* DHT library 2 | 3 | MIT license 4 | written by Adafruit Industries 5 | 6 | UPGRADED/Rewritten by Z-Wave>ME for project Z-Uno 2016 7 | 8 | */ 9 | #ifndef DHT_H 10 | #define DHT_H 11 | 12 | #include "Arduino.h" 13 | 14 | 15 | // Define types of sensors. 16 | #define DHT11 11 17 | #define DHT22 22 18 | #define DHT21 21 19 | #define AM2301 21 20 | 21 | #define BAD_DHT_VALUE 0xFFFF 22 | 23 | enum 24 | { 25 | DHT_RESULT_OK = 0, 26 | DHT_RESULT_PREVIOUS, 27 | DHT_RESULT_ERROR_NOSYNC, 28 | DHT_RESULT_ERROR_TIMEOUT, 29 | DHT_RESULT_ERROR_CRC 30 | 31 | }; 32 | 33 | 34 | class DHT { 35 | public: 36 | DHT(s_pin pin, uint8_t type = DHT22); 37 | void begin(void); 38 | // returns temperature in 10 th of Celsius 39 | int readTemperatureC10(bool force=false); 40 | // returns humidity in 10 th of percent 41 | int readHumidityH10(bool force=false); 42 | 43 | // Returns temperature as float in Celsius 44 | float readTemperature(bool force=false); 45 | // Returns humidity as float in pecents 46 | float readHumidity(bool force=false); 47 | 48 | // Just read raw data from sensor 49 | // Returns result code of operation (see enum) 50 | byte read(bool force=false); 51 | 52 | // Copies raw data from the last "read" operation to user buffer 53 | void getRawData(byte * ptr){ byte i; for(i=0;i<5;i++) ptr[i] = data_ptr[i];}; 54 | 55 | private: 56 | 57 | s_pin _pin; 58 | byte data_ptr[5]; 59 | 60 | int16_t humidity; 61 | int16_t temperature; 62 | uint8_t crc; 63 | 64 | uint8_t _type; 65 | uint32_t _lastreadtime, _maxcycles; 66 | bool _lastresult; 67 | 68 | 69 | }; 70 | 71 | 72 | #endif 73 | -------------------------------------------------------------------------------- /hardware/examples/DS18B20Scanner/DS18B20Scanner.ino: -------------------------------------------------------------------------------- 1 | /* 2 | * Sketch that scans 1-wire bus and prints all found 3 | * DS18B20 sensors ROMS and values. 4 | * (c) Z-Wave.Me 2016 5 | */ 6 | 7 | #include 8 | #include 9 | 10 | // LED pin number 11 | #define BUS_PIN 12 12 | #define ROM_SIZE 8 13 | #define MAX_SENSOR 8 14 | 15 | 16 | OneWire ow(BUS_PIN); 17 | DS18B20Sensor ds18b20(&ow); 18 | 19 | 20 | 21 | byte sensor_roms[ROM_SIZE*MAX_SENSOR]; 22 | byte number_of_sensors; 23 | 24 | #define MY_SERIAL Serial0 25 | 26 | #define ROM_DATA(index) (&sensor_roms[index*ROM_SIZE]) 27 | void printROM(byte * rom) 28 | { 29 | byte i; 30 | for(i=0; i<8; i++) 31 | { 32 | MY_SERIAL.print(" "); 33 | MY_SERIAL.print(rom[i], HEX); 34 | } 35 | } 36 | 37 | void setup() { 38 | 39 | MY_SERIAL.begin(115200); 40 | MY_SERIAL.println("Sketch is starting..."); 41 | number_of_sensors = ds18b20.findAllSensors(sensor_roms); 42 | MY_SERIAL.print("FOUND "); 43 | MY_SERIAL.print(number_of_sensors); 44 | MY_SERIAL.println(" DS18B20 sensor(s)"); 45 | byte i; 46 | 47 | for(i=0; i 99) { 32 | // by Z-Wave specification, this value can't be more then 99 33 | value = 99; 34 | } 35 | // but the LED brightness scale ranges from 0 to 255 36 | // we need to prepare our "value" for this new scale 37 | tempVariable = ((word)value)*255/99; 38 | 39 | // now we set the LED brightness 40 | analogWrite(PWM1, ((long)value)*255/99); 41 | 42 | // let's save our value for the situation, when the controller will ask us about it 43 | lastSetDimmer = value; 44 | } 45 | 46 | // getter function is called once the controller 47 | // or other device in the network asks Z-Uno about 48 | // it's current level 49 | byte getter(void) { 50 | // return previously saved (in getter()) value 51 | return lastSetDimmer; 52 | } 53 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/Print.h: -------------------------------------------------------------------------------- 1 | /* 2 | Print.h - Base class that provides print() and println() 3 | Copyright (c) 2008 David A. Mellis. All right reserved. 4 | 5 | Simplified for Z-Uno project by Z-Wave.Me (c) 2016 6 | */ 7 | 8 | #ifndef Print_h 9 | #define Print_h 10 | 11 | #include "ArduinoTypes.h" 12 | #include "c_lib_minimal.h" 13 | 14 | 15 | #define DEC 10 16 | #define HEX 16 17 | #define OCT 8 18 | #define BIN 2 19 | 20 | class Print 21 | { 22 | private: 23 | int write_error; 24 | size_t printNumber(unsigned long, uint8_t); 25 | size_t printFloat(float, uint8_t); 26 | size_t printByteArr(uint8_t * bytearr, uint8_t len, uint8_t base); 27 | protected: 28 | void setWriteError(int err = 1) { write_error = err; } 29 | public: 30 | Print() { write_error = 0; } 31 | 32 | int getWriteError() { return write_error; } 33 | void clearWriteError() { setWriteError(0); } 34 | 35 | virtual size_t write(uint8_t a){ return 0; };// = 0; 36 | virtual size_t write(uint8_t *buffer, size_t size); 37 | 38 | size_t print(char *); 39 | size_t print(char); 40 | size_t print(unsigned char, int = DEC); 41 | size_t print(int, int = DEC); 42 | size_t print(unsigned int, int = DEC); 43 | size_t print(long, int = DEC); 44 | size_t print(unsigned long, int = DEC); 45 | size_t print(float, int = 2); 46 | size_t print(double, int = 2); 47 | 48 | 49 | size_t println(char *); 50 | size_t println(char); 51 | size_t println(unsigned char, int = DEC); 52 | size_t println(int, int = DEC); 53 | size_t println(unsigned int, int = DEC); 54 | size_t println(long, int = DEC); 55 | size_t println(unsigned long, int = DEC); 56 | size_t println(float, int = 2); 57 | size_t println(double, int = 2); 58 | 59 | size_t println(void); 60 | 61 | }; 62 | 63 | #endif 64 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZMEKeypad/ZMEKeypad.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include "Arduino.h" 4 | 5 | 6 | // Lightwieght realisation of Keypad controller 7 | 8 | 9 | #define MAX_SCAN_KEYS 3 10 | struct KeyState_s 11 | { 12 | BYTE key_num; 13 | BYTE key_state; 14 | DWORD time; 15 | }; 16 | 17 | enum 18 | { 19 | KEYPAD_KEYSTATE_IDLE, 20 | KEYPAD_KEYSTATE_DEBOUNCE, 21 | KEYPAD_KEYSTATE_PRESSED, 22 | KEYPAD_KEYSTATE_HOLDED 23 | 24 | }; 25 | 26 | 27 | #define DEBOUNCE_DEFAULT_TIME 10 28 | #define HOLD_DEFAULT_TIME 200 29 | 30 | #define KEYPAD_KEYINDEX(A) (A & ~(0x80)) 31 | #define KEYPAD_IS_HOLDING(A) (A & (0x80)) 32 | 33 | 34 | 35 | class ZMEKeypad 36 | { 37 | 38 | public: 39 | ZMEKeypad(BYTE * colums, BYTE numcols, BYTE * rows, BYTE numrows); 40 | 41 | // You have to poll this function in the loop 42 | // Returns number of pressed keys 43 | // OUT: key_actions 44 | BYTE scanKeys(BYTE * key_actions); 45 | 46 | // You can use this as superclass and overrite these functions 47 | // for another hartware. 48 | virtual void m_pinMode(BYTE pin, BYTE mode) { pinMode(pin, mode);}; 49 | virtual BYTE m_pinGet(BYTE pin) { return digitalRead(pin); }; 50 | virtual void m_pinSet(BYTE pin, BYTE value) { digitalWrite(pin, value); }; 51 | 52 | // Initializes keyscanner 53 | void begin(); 54 | void clearKeys(){mon_keys = 0;}; 55 | 56 | // You can setup hold/debounce intervals in the 10th of microseconds 57 | void setHoldTime(BYTE tm){hold_time = tm;}; 58 | void setDebounceTime(BYTE tm){debounce_time = tm;}; 59 | 60 | // Checks if all the buttons was released 61 | BYTE isIdled(){return mon_keys == 0;}; 62 | 63 | private: 64 | 65 | BYTE * column_vec; 66 | BYTE * row_vec; 67 | BYTE n_col, n_row; 68 | 69 | KeyState_s key_states[MAX_SCAN_KEYS]; 70 | BYTE mon_keys; 71 | 72 | BYTE debounce_time; 73 | BYTE hold_time; 74 | 75 | 76 | 77 | }; -------------------------------------------------------------------------------- /hardware/examples/Keypad4x4/Keypad4x4.ino: -------------------------------------------------------------------------------- 1 | 2 | // This skethc demonstrate use of KeyPad 4x4 with Z-Uno 3 | #include 4 | // Define number of rows 5 | #define ROWS 4 6 | // Define number of columns 7 | #define COLS 4 8 | 9 | 10 | 11 | // Define pins numbers that we use for rows 12 | BYTE rowPins[4] = {9, 10, 11, 12}; 13 | // Define pins numbers that we use for volumns 14 | BYTE columnPins[4] = {14, 15, 16, 17}; 15 | 16 | // Titlse for all buttons in one string 17 | char keys[] = "123A456B789C*0#D"; 18 | 19 | 20 | 21 | #define ledpin 13 22 | // Construct keypad object 23 | ZMEKeypad kpd = ZMEKeypad(columnPins, COLS, rowPins, ROWS); 24 | 25 | 26 | void setup() 27 | { 28 | pinMode(ledpin,OUTPUT); 29 | digitalWrite(ledpin, LOW); 30 | Serial.begin(); 31 | 32 | // Init keypad 33 | kpd.begin(); 34 | Serial.println("Sketch is starting..."); 35 | 36 | } 37 | 38 | void loop() 39 | { 40 | byte actions[4]; 41 | byte num_touched_keys = kpd.scanKeys(actions); 42 | 43 | // We can process a number of buttons during one scan 44 | for(byte i=0;i>> ZUNO loop #"); 26 | Serial1.print(g_counter, HEX); 27 | Serial1.print(" <<<\n"); 28 | 29 | g_counter++; 30 | 31 | return; 32 | } 33 | // Рекурсивная функция, проверяющая возможности стека 34 | void testStackR(byte max_deep) 35 | { 36 | 37 | Serial1.print("\n Deep remains:"); 38 | Serial1.println(max_deep, DEC); 39 | Serial1.print("\n Deep trigonometry:"); 40 | Serial1.println(sin(0.01157894*max_deep),7); 41 | 42 | if(!max_deep) 43 | { 44 | //printUART1Str("\n\n @@@ Hello world from deep stack! @@@\n\n"); 45 | Serial1.print("\n\n @@@ Hello world from deep stack! @@@\n\n"); 46 | return; 47 | } 48 | 49 | 50 | 51 | testStackR(max_deep - 1); 52 | } 53 | 54 | 55 | void loop() { 56 | 57 | 58 | float sin_res = sin(PI*0.25);//0.7108456;//sinf(3.14*0.25); 59 | 60 | 61 | 62 | Serial1.print("Millis:"); 63 | Serial1.println(millis()); 64 | 65 | 66 | Serial1.print("Some float:"); 67 | Serial1.println(sin_res); 68 | Serial1.println(sin_res,7); 69 | 70 | 71 | digitalWrite(LED_PIN, HIGH); // turn LED on 72 | delay(1000); // wait for 1 second 73 | digitalWrite(LED_PIN, LOW); // turn LED off 74 | testStack(); 75 | delay(1000); 76 | 77 | testStackR(10); 78 | 79 | } 80 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/boards.txt: -------------------------------------------------------------------------------- 1 | # See: http://code.google.com/p/arduino/wiki/Platforms 2 | 3 | menu.cpu=Processor 4 | menu.Frequency=Frequency 5 | menu.Security=Security 6 | #menu.MuliCommand=Multicommand 7 | 8 | ############################################################## 9 | zuno.name=Z-Wave>ME Z-Uno 10 | 11 | zuno.vid.0=0x0658 12 | zuno.pid.0=0x0200 13 | zuno.vid.1=0x0658 14 | zuno.pid.1=0x0000 15 | 16 | zuno.upload.tool=zprog 17 | zuno.upload.protocol=usb 18 | zuno.upload.maximum_size=32256 19 | zuno.upload.maximum_data_size=0 20 | zuno.upload.speed=115200 21 | 22 | zuno.bootloader.tool=zprog 23 | zuno.bootloader.low_fuses=0xFF 24 | zuno.bootloader.high_fuses=0xDE 25 | zuno.bootloader.extended_fuses=0x05 26 | zuno.bootloader.unlock_bits=0x3F 27 | zuno.bootloader.lock_bits=0x0F 28 | zuno.bootloader.file=none 29 | 30 | zuno.build.mcu=zuno 31 | zuno.build.f_cpu=16000000L 32 | zuno.build.board=zuno 33 | zuno.build.core=zuno 34 | zuno.build.variant= 35 | zuno.build.vid=0x2341 36 | zuno.build.pid=0x8039 37 | zuno.build.usb_product="Z-UNO" 38 | zuno.build.extra_flags= 39 | 40 | zuno.menu.Frequency.Ru = Russian 41 | zuno.menu.Frequency.Eu = Europe 42 | zuno.menu.Frequency.Us = USA 43 | zuno.menu.Frequency.In = India 44 | zuno.menu.Frequency.Il = Israel 45 | zuno.menu.Frequency.ANz = Australia & New Zealand, Brazil 46 | zuno.menu.Frequency.Ch = China 47 | zuno.menu.Frequency.Hk = Hong Kong 48 | 49 | 50 | zuno.menu.Frequency.Ru.build.rf_freq = RU 51 | zuno.menu.Frequency.Eu.build.rf_freq = EU 52 | zuno.menu.Frequency.Us.build.rf_freq = US 53 | zuno.menu.Frequency.In.build.rf_freq = IN 54 | zuno.menu.Frequency.Il.build.rf_freq = IL 55 | zuno.menu.Frequency.ANz.build.rf_freq = ANZ 56 | zuno.menu.Frequency.Ch.build.rf_freq = CN 57 | zuno.menu.Frequency.Hk.build.rf_freq = HK 58 | 59 | 60 | zuno.menu.Security.Off = Disabled 61 | zuno.menu.Security.On = Enabled 62 | zuno.menu.Security.Off.build.security = 0 63 | zuno.menu.Security.On.build.security = 1 64 | 65 | #zuno.menu.MuliCommand.Off = Disabled 66 | #zuno.menu.MuliCommand.On = Enabled 67 | #zuno.menu.MuliCommand.Off.build.multicmd = 0 68 | #zuno.menu.MuliCommand.On.build.multicmd = 1 69 | -------------------------------------------------------------------------------- /hardware/examples/MotionSensor/MotionSensor.ino: -------------------------------------------------------------------------------- 1 | /* 2 | * That is a Simple Sensor Motion example 3 | * It watches over the built in button state 4 | * And sends report to the controller if detects motion 5 | */ 6 | 7 | // built in LED number 8 | #define LED_PIN 13 9 | 10 | // motion trigger pin 11 | #define MOTION_PIN 12 12 | 13 | // channel number 14 | #define ZUNO_CHANNEL_NUMBER_ONE 1 15 | 16 | // next macro sets up the Z-Uno channels 17 | // in this example we set up 1 sensor binary channel 18 | // you can read more on http://z-uno.z-wave.me/Reference/ZUNO_SENSOR_BINARY/ 19 | ZUNO_SETUP_CHANNELS(ZUNO_SENSOR_BINARY(ZUNO_SENSOR_BINARY_TYPE_MOTION, getter)); 20 | 21 | // variable to store current motion state 22 | byte lastSensorValue = 0; 23 | 24 | void setup(){ 25 | //enable usb printing 26 | Serial.begin(); 27 | pinMode(LED_PIN, OUTPUT); // set LED pin as output 28 | pinMode(MOTION_PIN,INPUT); // set motion pin as input 29 | } 30 | 31 | void loop(){ 32 | // sample current motion state 33 | byte currentSensorValue = digitalRead(MOTION_PIN); 34 | 35 | if (currentSensorValue != lastSensorValue) { // if motion state changes 36 | lastSensorValue = currentSensorValue; // save new state 37 | zunoSendReport(ZUNO_CHANNEL_NUMBER_ONE); // send report over the Z-Wave to the controller 38 | if (currentSensorValue == HIGH){ // is there is motion 39 | Serial.println("Motion detected"); // send message over USB 40 | digitalWrite(LED_PIN, HIGH); // turn LED on 41 | } else { // if motion ended 42 | Serial.println("Motion stopped"); // send message over USB 43 | digitalWrite(LED_PIN, LOW); // turn LED off 44 | } 45 | } 46 | } 47 | 48 | // function, which returns the previously saved button state 49 | // this function runs only once the controller asks 50 | byte getter(){ 51 | if (lastSensorValue == 1) { // if motion is detected 52 | return 0xff; // return "Triggered" state to the controller 53 | } else { // if motion stopped 54 | return 0; // return "Idle" state to the controller 55 | } 56 | } 57 | 58 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/EEPROM.cpp: -------------------------------------------------------------------------------- 1 | #include "EEPROM.h" 2 | #include "ZUNO_call_proto.h" 3 | 4 | #define WRITE_FUNC (rfunc + 1) 5 | #define READ_FUNC (rfunc) 6 | 7 | 8 | word EEPROMClass::put(DWORD address, void * value, word val_size) 9 | { 10 | zunoPushWord(reinterpPOINTER((byte*)value)); 11 | zunoPushWord(val_size); 12 | zunoPushDword(address); 13 | zunoPushByte(WRITE_FUNC); 14 | zunoCall(); 15 | return zunoPopWord(); 16 | } 17 | word EEPROMClass::get(DWORD address, void * value, word val_size) 18 | { 19 | zunoPushWord(reinterpPOINTER((byte*)value)); 20 | zunoPushWord(val_size); 21 | zunoPushDword(address); 22 | zunoPushByte(READ_FUNC); 23 | zunoCall(); 24 | return zunoPopWord(); 25 | } 26 | byte EEPROMClass::read(DWORD address) 27 | { 28 | get(address, &temp_byte, 1); 29 | return temp_byte; 30 | } 31 | void EEPROMClass::update(DWORD address, byte value) 32 | { 33 | get(address, &temp_byte, 1); 34 | 35 | if(value != temp_byte) 36 | { 37 | temp_byte = value; 38 | put(address, &temp_byte, 1); 39 | } 40 | 41 | } 42 | void EEPROMClass::write(DWORD address, byte value) 43 | { 44 | temp_byte = value; 45 | put(address, &temp_byte, 1); 46 | 47 | } 48 | 49 | byte NZRAMClass::put(byte address, void * value, byte val_size) 50 | { 51 | zunoPushWord(reinterpPOINTER((byte*)value)); 52 | zunoPushByte(val_size); 53 | zunoPushByte(address); 54 | zunoPushByte(WRITE_FUNC); 55 | zunoCall(); 56 | return zunoPopByte(); 57 | } 58 | byte NZRAMClass::get(byte address, void * value, byte val_size) 59 | { 60 | zunoPushWord(reinterpPOINTER((byte*)value)); 61 | zunoPushByte(val_size); 62 | zunoPushByte(address); 63 | zunoPushByte(READ_FUNC); 64 | zunoCall(); 65 | return zunoPopByte(); 66 | } 67 | byte NZRAMClass::read(byte address) 68 | { 69 | get(address, &temp_byte, 1); 70 | return temp_byte; 71 | } 72 | void NZRAMClass::update(byte address, byte value) 73 | { 74 | get(address, &temp_byte, 1); 75 | 76 | if(value != temp_byte) 77 | { 78 | temp_byte = value; 79 | put(address, &temp_byte, 1); 80 | } 81 | 82 | } 83 | void NZRAMClass::write(byte address, byte value) 84 | { 85 | temp_byte = value; 86 | put(address, &temp_byte, 1); 87 | } 88 | 89 | EEPROMClass EEPROM(ZUNO_FUNC_EEPROM_READ); 90 | NZRAMClass NZRAM(ZUNO_FUNC_NZRAM_READ); 91 | -------------------------------------------------------------------------------- /hardware/examples/BMP180Test/BMP180Test.ino: -------------------------------------------------------------------------------- 1 | /*************************************************** 2 | This is an example for the BMP180 Barometric Pressure & Temp Sensor 3 | 4 | Designed specifically to work with the Adafruit BMP085 Breakout 5 | ----> https://www.adafruit.com/products/391 6 | 7 | These displays use I2C to communicate, 2 pins are required to 8 | interface 9 | Adafruit invests time and resources providing this open source code, 10 | please support Adafruit and open-source hardware by purchasing 11 | products from Adafruit! 12 | 13 | Written by Limor Fried/Ladyada for Adafruit Industries. 14 | 15 | 2016 Adoptated for Z-Uno project by Z-Wave>ME 16 | 17 | BSD license, all text above must be included in any redistribution 18 | ****************************************************/ 19 | 20 | // Connect VCC of the BMP085 sensor to 3.3V (NOT 5.0V!) 21 | // Connect GND to Ground 22 | // Connect SCL to i2c clock - on Z-Uno thats Digital 9 23 | // Connect SDA to i2c data - on Z-Uno thats Digital 10 24 | // EOC is not used, it signifies an end of conversion 25 | // XCLR is a reset pin, also not used here 26 | 27 | #include 28 | #include 29 | 30 | 31 | 32 | ZUNO_BMP180 bmp; 33 | 34 | void setup() { 35 | Serial.begin(); 36 | if (!bmp.begin()) { 37 | Serial.println("Could not find a valid BMP180 sensor, check wiring!"); 38 | } 39 | } 40 | 41 | void loop() { 42 | 43 | delay(1000); 44 | // Get Temperature 45 | Serial.print("Temperature = "); 46 | Serial.print(bmp.readTemperature()); 47 | Serial.println(" *C"); 48 | 49 | // Get Pressure 50 | Serial.print("Pressure = "); 51 | Serial.print(bmp.readPressure()); 52 | Serial.println(" Pa"); 53 | 54 | // Calculate altitude assuming 'standard' barometric 55 | // pressure of 1013.25 millibar = 101325 Pascal 56 | Serial.print("Altitude = "); 57 | Serial.print(bmp.readAltitude()); 58 | Serial.println(" meters"); 59 | 60 | // you can get a more precise measurement of altitude 61 | // if you know the current sea level pressure which will 62 | // vary with weather and such. If it is 1015 millibars 63 | // that is equal to 101500 Pascals. 64 | Serial.print("Real altitude = "); 65 | Serial.print(bmp.readAltitude(99082)); 66 | Serial.println(" meters"); 67 | 68 | Serial.println(); 69 | 70 | delay(2000); 71 | } -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/HardwareSerial.cpp: -------------------------------------------------------------------------------- 1 | 2 | #include "HardwareSerial.h" 3 | #include "ZUNO_Definitions.h" 4 | #include "ZUNO_call_proto.h" 5 | 6 | // Чтобы было проще настраивать потом - определяем смещения от первого enum 7 | #define FUNC_START(num) (num) 8 | #define FUNC_END(num) (num + 1) 9 | #define FUNC_AVAILIABLE(num) (num + 2) 10 | #define FUNC_READ(num) (num + 3) 11 | #define FUNC_WRITE(num) (num + 4) 12 | 13 | 14 | 15 | //word g_write_counter = 0; 16 | 17 | HardwareSerial::HardwareSerial(BYTE number) 18 | { 19 | func_vec = number; 20 | } 21 | 22 | 23 | void HardwareSerial::begin() 24 | { 25 | zunoPushWord(1152); //default baudrate is 115200 26 | zunoPushByte(FUNC_START(func_vec)); 27 | zunoCall(); 28 | } 29 | 30 | void HardwareSerial::begin(DWORD baudrate) 31 | { 32 | WORD correct_dbrt = (WORD)(baudrate / 100); 33 | zunoPushWord(correct_dbrt); 34 | zunoPushByte(FUNC_START(func_vec)); 35 | zunoCall(); 36 | } 37 | void HardwareSerial::end() 38 | { 39 | zunoPushByte(FUNC_END(func_vec)); 40 | zunoCall(); 41 | } 42 | int HardwareSerial::available(void) 43 | { 44 | zunoPushByte(FUNC_AVAILIABLE(func_vec)); 45 | zunoCall(); 46 | return zunoPopByte(); 47 | } 48 | int HardwareSerial::peek(void) 49 | { 50 | byte res = 0; 51 | zunoPushByte(FUNC_AVAILIABLE(func_vec)); 52 | zunoCall(); 53 | res = zunoPopByte(); 54 | if(!res) 55 | return -1; 56 | zunoPushByte(FALSE); // not to remove byte from read buffer 57 | zunoPushByte(FUNC_READ(func_vec)); 58 | zunoCall(); 59 | return zunoPopByte(); 60 | } 61 | int HardwareSerial::read(void) 62 | { 63 | zunoPushByte(TRUE); // remove byte from read buffer 64 | zunoPushByte(FUNC_READ(func_vec)); 65 | zunoCall(); 66 | return zunoPopByte(); 67 | } 68 | void HardwareSerial::flush(void) 69 | { 70 | 71 | } 72 | size_t HardwareSerial::write(uint8_t value) 73 | { 74 | 75 | //g_write_counter++; 76 | zunoPushByte(value); 77 | zunoPushByte(FUNC_WRITE(func_vec)); 78 | zunoCall(); 79 | 80 | 81 | // Несоотвествие ардуиновскому вызову 82 | // должно быть 83 | // return zunoPopByte(); 84 | // которое возвращает либо 0 - байт не записан, либо 1 - байт записан 85 | return 1; 86 | } 87 | 88 | // Экземпляры классов - стиль как в Ардуино 89 | HardwareSerial Serial(ZUNO_FUNC_SERIAL_USB_BEGIN); // USB 90 | HardwareSerial Serial1(ZUNO_FUNC_SERIAL1_BEGIN); // UART0 91 | HardwareSerial Serial0(ZUNO_FUNC_SERIAL0_BEGIN); // UART1 - Нужно его добавить, пока это тот же UART0 -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_BH1750/ZUNO_BH1750.cpp: -------------------------------------------------------------------------------- 1 | /*************************************************** 2 | This is a library for the BH1750(FVI) light sensor 3 | This sensor use I2C to communicate, 2 pins are required to 4 | interface 5 | Datasheet: 6 | http://rohmfs.rohm.com/en/products/databook/datasheet/ic/sensor/light/bh1750fvi-e.pdf 7 | Based on BH1750 lib written by Christopher Laws, March, 2013. 8 | Adapted to ZUNO 9 | ****************************************************/ 10 | 11 | #include "ZUNO_BH1750.h" 12 | #include "Wire.h" 13 | 14 | #define BH1750_DEBUG 0 15 | 16 | BH1750::BH1750() { 17 | 18 | } 19 | 20 | void BH1750::begin(uint8_t mode, uint8_t addr) { 21 | 22 | Wire.begin(); 23 | // initialization sensor 24 | configure(mode, addr); 25 | } 26 | 27 | void BH1750::configure(uint8_t mode, uint8_t addr) { 28 | 29 | Wire.beginTransmission(addr); 30 | switch (mode) { 31 | case BH1750_CONTINUOUS_HIGH_RES_MODE: 32 | case BH1750_CONTINUOUS_HIGH_RES_MODE_2: 33 | case BH1750_CONTINUOUS_LOW_RES_MODE: 34 | case BH1750_ONE_TIME_HIGH_RES_MODE: 35 | case BH1750_ONE_TIME_HIGH_RES_MODE_2: 36 | case BH1750_ONE_TIME_LOW_RES_MODE: 37 | // apply a valid mode change 38 | Wire.write(mode); 39 | delay(10); 40 | break; 41 | default: 42 | // Invalid measurement mode 43 | #if BH1750_DEBUG == 1 44 | Serial.println("Invalid measurement mode"); 45 | #endif 46 | break; 47 | } 48 | Wire.endTransmission(); 49 | } 50 | 51 | void BH1750::powerOn(uint8_t addr) { 52 | Wire.beginTransmission(addr); 53 | Wire.write(BH1750_POWER_ON); 54 | Wire.endTransmission(); 55 | } 56 | void BH1750::powerDown(uint8_t addr) { 57 | Wire.beginTransmission(addr); 58 | Wire.write(BH1750_POWER_DOWN); 59 | Wire.endTransmission(); 60 | } 61 | void BH1750::reset(uint8_t addr) { 62 | Wire.beginTransmission(addr); 63 | Wire.write(BH1750_RESET); 64 | Wire.endTransmission(); 65 | } 66 | 67 | uint16_t BH1750::readLightLevel(uint8_t addr) { 68 | 69 | uint16_t level; 70 | 71 | Wire.beginTransmission(addr); 72 | Wire.requestFrom(addr, 2); 73 | 74 | level = Wire.read(); 75 | level <<= 8; 76 | level |= Wire.read(); 77 | 78 | Wire.endTransmission(); 79 | 80 | #if BH1750_DEBUG == 1 81 | Serial.print("Raw light level: "); 82 | Serial.println(level); 83 | #endif 84 | 85 | level = level/1.2; // convert to lux 86 | 87 | #if BH1750_DEBUG == 1 88 | Serial.print("Light level: "); 89 | Serial.println(level); 90 | #endif 91 | return level; 92 | } -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/Wire.h: -------------------------------------------------------------------------------- 1 | /* 2 | TwoWire.h - TWI/I2C library for Arduino & Wiring 3 | Copyright (c) 2006 Nicholas Zambetti. All right reserved. 4 | 5 | This library is free software; you can redistribute it and/or 6 | modify it under the terms of the GNU Lesser General Public 7 | License as published by the Free Software Foundation; either 8 | version 2.1 of the License, or (at your option) any later version. 9 | 10 | This library is distributed in the hope that it will be useful, 11 | but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 13 | Lesser General Public License for more details. 14 | 15 | You should have received a copy of the GNU Lesser General Public 16 | License along with this library; if not, write to the Free Software 17 | Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 18 | 19 | Modified 2012 by Todd Krein (todd@krein.org) to implement repeated starts 20 | Modified 2016 by Z-Wave>Me (info@z-wave.me) for Z-Uno project 21 | */ 22 | 23 | #pragma once 24 | 25 | #include "Stream.h" 26 | 27 | 28 | 29 | // DEFAULT I2C PINS 30 | #define SCL_PIN 9 31 | #define SDA_PIN 10 32 | 33 | 34 | 35 | class I2CDriver 36 | { 37 | 38 | public: 39 | I2CDriver(s_pin scl = 9, s_pin sda = 10); 40 | void bind(void); 41 | void start(void); 42 | void stop(void); 43 | byte write(byte b); 44 | byte read(byte ack); 45 | 46 | private: 47 | 48 | s_pin _scl; 49 | s_pin _sda; 50 | 51 | }; 52 | class TwoWire : public Stream 53 | { 54 | private: 55 | 56 | uint8_t txAddress; 57 | uint8_t available_bytes; 58 | uint8_t state; 59 | uint8_t b_flags; 60 | uint8_t sucess_code; 61 | 62 | I2CDriver * p_driver; 63 | 64 | 65 | 66 | public: 67 | TwoWire(I2CDriver * driver = NULL); 68 | void begin(I2CDriver * driver = NULL); 69 | void bindDriver(I2CDriver * driver); 70 | void beginTransmission(uint8_t, uint8_t forced_write = false); 71 | uint8_t endTransmission(uint8_t stop = true); 72 | uint8_t requestFrom(uint8_t, uint8_t, bool stop = true); 73 | virtual size_t write(uint8_t); 74 | virtual int available(void); 75 | virtual int read(void); 76 | virtual int peek(void); 77 | virtual void flush(void); 78 | 79 | 80 | size_t write(unsigned long n) { return write((uint8_t)n); } 81 | size_t write(long n) { return write((uint8_t)n); } 82 | size_t write(unsigned int n) { return write((uint8_t)n); } 83 | size_t write(int n) { return write((uint8_t)n); } 84 | 85 | }; 86 | 87 | 88 | extern TwoWire Wire; 89 | 90 | 91 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_MCP23017/ZUNO_MCP23017.h: -------------------------------------------------------------------------------- 1 | /*************************************************** 2 | This is a library for the MCP23017 i2c port expander 3 | 4 | These displays use I2C to communicate, 2 pins are required to 5 | interface 6 | Adafruit invests time and resources providing this open source code, 7 | please support Adafruit and open-source hardware by purchasing 8 | products from Adafruit! 9 | 10 | Written by Limor Fried/Ladyada for Adafruit Industries. 11 | BSD license, all text above must be included in any redistribution 12 | 13 | Adoptated for Z-Uno project by Z-Wave>ME 2016 14 | ****************************************************/ 15 | 16 | #ifndef _ZUNO_MCP23017_H_ 17 | #define _ZUNO_MCP23017_H_ 18 | 19 | #include 20 | 21 | 22 | class ZUNO_MCP23017 { 23 | public: 24 | ZUNO_MCP23017(){}; 25 | void begin(uint8_t addr); 26 | void begin(void); 27 | 28 | void pinMode(uint8_t p, uint8_t d); 29 | void digitalWrite(uint8_t p, uint8_t d); 30 | void pullUp(uint8_t p, uint8_t d); 31 | uint8_t digitalRead(uint8_t p); 32 | 33 | void writeGPIOAB(uint16_t); 34 | uint16_t readGPIOAB(); 35 | uint8_t readGPIO(uint8_t b); 36 | 37 | void setupInterrupts(uint8_t mirroring, uint8_t open, uint8_t polarity); 38 | void setupInterruptPin(uint8_t p, uint8_t mode); 39 | uint8_t getLastInterruptPin(); 40 | uint8_t getLastInterruptPinValue(); 41 | 42 | private: 43 | uint8_t i2caddr; 44 | 45 | uint8_t bitForPin(uint8_t pin); 46 | uint8_t regForPin(uint8_t pin, uint8_t portAaddr, uint8_t portBaddr); 47 | 48 | uint8_t readRegister(uint8_t addr); 49 | void writeRegister(uint8_t addr, uint8_t value); 50 | 51 | /** 52 | * Utility private method to update a register associated with a pin (whether port A/B) 53 | * reads its value, updates the particular bit, and writes its value. 54 | */ 55 | void updateRegisterBit(uint8_t p, uint8_t pValue, uint8_t portAaddr, uint8_t portBaddr); 56 | 57 | }; 58 | 59 | #define MCP23017_ADDRESS 0x20 60 | 61 | // registers 62 | #define MCP23017_IODIRA 0x00 63 | #define MCP23017_IPOLA 0x02 64 | #define MCP23017_GPINTENA 0x04 65 | #define MCP23017_DEFVALA 0x06 66 | #define MCP23017_INTCONA 0x08 67 | #define MCP23017_IOCONA 0x0A 68 | #define MCP23017_GPPUA 0x0C 69 | #define MCP23017_INTFA 0x0E 70 | #define MCP23017_INTCAPA 0x10 71 | #define MCP23017_GPIOA 0x12 72 | #define MCP23017_OLATA 0x14 73 | 74 | 75 | #define MCP23017_IODIRB 0x01 76 | #define MCP23017_IPOLB 0x03 77 | #define MCP23017_GPINTENB 0x05 78 | #define MCP23017_DEFVALB 0x07 79 | #define MCP23017_INTCONB 0x09 80 | #define MCP23017_IOCONB 0x0B 81 | #define MCP23017_GPPUB 0x0D 82 | #define MCP23017_INTFB 0x0F 83 | #define MCP23017_INTCAPB 0x11 84 | #define MCP23017_GPIOB 0x13 85 | #define MCP23017_OLATB 0x15 86 | 87 | #define MCP23017_INT_ERR 255 88 | 89 | #endif 90 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_BH1750/ZUNO_BH1750.h: -------------------------------------------------------------------------------- 1 | /*************************************************** 2 | This is a library for the BH1750(FVI) light sensor 3 | This sensor use I2C to communicate, 2 pins are required to 4 | interface 5 | Datasheet: 6 | http://rohmfs.rohm.com/en/products/databook/datasheet/ic/sensor/light/bh1750fvi-e.pdf 7 | Based on BH1750 lib written by Christopher Laws, March, 2013. 8 | Adapted to ZUNO 9 | ****************************************************/ 10 | 11 | #ifndef BH1750_h 12 | #define BH1750_h 13 | 14 | #include "Arduino.h" 15 | 16 | // BH1750 address on the I2C bus, depending on the level of ADDR pin 17 | #define BH1750_I2CADDR_L 0x23 18 | #define BH1750_I2CADDR_H 0x5C 19 | // define low address as default 20 | #define BH1750_I2CADDR BH1750_I2CADDR_L 21 | 22 | // No active state 23 | #define BH1750_POWER_DOWN 0x00 24 | 25 | // Wating for measurment command 26 | #define BH1750_POWER_ON 0x01 27 | 28 | // Reset data register value - not accepted in POWER_DOWN mode 29 | #define BH1750_RESET 0x07 30 | 31 | // Start measurement at 1 lx resolution. Measurement time is approx 120ms. 32 | #define BH1750_CONTINUOUS_HIGH_RES_MODE 0x10 33 | 34 | // Start measurement at 0.5 lx resolution. Measurement time is approx 120ms. 35 | #define BH1750_CONTINUOUS_HIGH_RES_MODE_2 0x11 36 | 37 | // Start measurement at 4 lx resolution. Measurement time is approx 16ms. 38 | #define BH1750_CONTINUOUS_LOW_RES_MODE 0x13 39 | 40 | // Start measurement at 1 lx resolution. Measurement time is approx 120ms. 41 | // Device is automatically set to Power Down after measurement. 42 | #define BH1750_ONE_TIME_HIGH_RES_MODE 0x20 43 | 44 | // Start measurement at 0.5 lx resolution. Measurement time is approx 120ms. 45 | // Device is automatically set to Power Down after measurement. 46 | #define BH1750_ONE_TIME_HIGH_RES_MODE_2 0x21 47 | 48 | // Start measurement at 1 lx resolution. Measurement time is approx 120ms. 49 | // Device is automatically set to Power Down after measurement. 50 | #define BH1750_ONE_TIME_LOW_RES_MODE 0x23 51 | 52 | // max measurement times in ms 53 | #define BH1750_LOW_RES_MODE_MAXTIME 24 54 | #define BH1750_HIGH_RES_MODE_MAXTIME 180 55 | #define BH1750_HIGH_RES_MODE_2_MAXTIME 180 56 | 57 | 58 | class BH1750 { 59 | public: 60 | BH1750(); 61 | void begin(uint8_t mode = BH1750_CONTINUOUS_HIGH_RES_MODE, uint8_t addr = BH1750_I2CADDR_L); 62 | void configure(uint8_t mode = BH1750_CONTINUOUS_HIGH_RES_MODE, uint8_t addr = BH1750_I2CADDR_L); 63 | void powerOn(uint8_t addr = BH1750_I2CADDR_L); 64 | void powerDown(uint8_t addr = BH1750_I2CADDR_L); 65 | void reset(uint8_t addr = BH1750_I2CADDR_L); 66 | uint16_t readLightLevel(uint8_t addr = BH1750_I2CADDR_L); 67 | 68 | private: 69 | uint8_t test; // dummy to get rid of error during compilation if no private part exist 70 | }; 71 | 72 | #endif -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_MCP4725/ZUNO_MCP4725.cpp: -------------------------------------------------------------------------------- 1 | /**************************************************************************/ 2 | /*! 3 | @file Adafruit_MCP4725.cpp 4 | @author K.Townsend (Adafruit Industries) 5 | @license BSD (see license.txt) 6 | 7 | I2C Driver for Microchip's MCP4725 I2C DAC 8 | 9 | This is a library for the Adafruit MCP4725 breakout 10 | ----> http://www.adafruit.com/products/935 11 | 12 | Adafruit invests time and resources providing this open source code, 13 | please support Adafruit and open-source hardware by purchasing 14 | products from Adafruit! 15 | 16 | @section HISTORY 17 | 18 | v1.0 - First release 19 | some changes for Z-Uno by m.p. 22.11.2016 20 | @file ZUNO_MCP4725.cpp 21 | 22 | */ 23 | /**************************************************************************/ 24 | #include 25 | 26 | #include "ZUNO_MCP4725.h" 27 | 28 | /**************************************************************************/ 29 | /*! 30 | @brief Instantiates a new MCP4725 class 31 | */ 32 | /**************************************************************************/ 33 | ZUNO_MCP4725::ZUNO_MCP4725() { 34 | } 35 | 36 | /**************************************************************************/ 37 | /*! 38 | @brief Setups the HW 39 | */ 40 | /**************************************************************************/ 41 | void ZUNO_MCP4725::begin(uint8_t addr) { 42 | _i2caddr = addr; 43 | Wire.begin(); 44 | 45 | } 46 | 47 | /**************************************************************************/ 48 | /*! 49 | @brief Sets the output voltage to a fraction of source vref. (Value 50 | can be 0..4095) 51 | 52 | @param[in] output 53 | The 12-bit value representing the relationship between 54 | the DAC's input voltage and its output voltage. 55 | @param[in] writeEEPROM 56 | If this value is true, 'output' will also be written 57 | to the MCP4725's internal non-volatile memory, meaning 58 | that the DAC will retain the current voltage output 59 | after power-down or reset. 60 | */ 61 | /**************************************************************************/ 62 | void ZUNO_MCP4725::setVoltage( uint16_t output, bool writeEEPROM ) 63 | { 64 | #ifdef TWBR 65 | uint8_t twbrback = TWBR; 66 | TWBR = ((F_CPU / 400000L) - 16) / 2; // Set I2C frequency to 400kHz 67 | #endif 68 | Wire.beginTransmission(_i2caddr); 69 | if (writeEEPROM) 70 | { 71 | Wire.write(MCP4726_CMD_WRITEDACEEPROM); 72 | } 73 | else 74 | { 75 | Wire.write(MCP4726_CMD_WRITEDAC); 76 | } 77 | Wire.write(output / 16); // Upper data bits (D11.D10.D9.D8.D7.D6.D5.D4) 78 | Wire.write((output % 16) << 4); // Lower data bits (D3.D2.D1.D0.x.x.x.x) 79 | Wire.endTransmission(); 80 | #ifdef TWBR 81 | TWBR = twbrback; 82 | #endif 83 | } 84 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_BMP180/ZUNO_BMP180.h: -------------------------------------------------------------------------------- 1 | /*************************************************** 2 | This is a library for the Adafruit BMP085/BMP180 Barometric Pressure + Temp sensor 3 | 4 | Designed specifically to work with the Adafruit BMP085 or BMP180 Breakout 5 | ----> http://www.adafruit.com/products/391 6 | ----> http://www.adafruit.com/products/1603 7 | 8 | These displays use I2C to communicate, 2 pins are required to 9 | interface 10 | Adafruit invests time and resources providing this open source code, 11 | please support Adafruit and open-source hardware by purchasing 12 | products from Adafruit! 13 | 14 | Written by Limor Fried/Ladyada for Adafruit Industries. 15 | BSD license, all text above must be included in any redistribution 16 | ****************************************************/ 17 | 18 | #ifndef ADAFRUIT_BMP085_H 19 | #define ADAFRUIT_BMP085_H 20 | 21 | #include "Arduino.h" 22 | 23 | #define BMP085_DEBUG 0 24 | 25 | #define BMP085_I2CADDR 0x77 26 | 27 | #define BMP085_ULTRALOWPOWER 0 28 | #define BMP085_STANDARD 1 29 | #define BMP085_HIGHRES 2 30 | #define BMP085_ULTRAHIGHRES 3 31 | #define BMP085_CAL_AC1 0xAA // R Calibration data (16 bits) 32 | #define BMP085_CAL_AC2 0xAC // R Calibration data (16 bits) 33 | #define BMP085_CAL_AC3 0xAE // R Calibration data (16 bits) 34 | #define BMP085_CAL_AC4 0xB0 // R Calibration data (16 bits) 35 | #define BMP085_CAL_AC5 0xB2 // R Calibration data (16 bits) 36 | #define BMP085_CAL_AC6 0xB4 // R Calibration data (16 bits) 37 | #define BMP085_CAL_B1 0xB6 // R Calibration data (16 bits) 38 | #define BMP085_CAL_B2 0xB8 // R Calibration data (16 bits) 39 | #define BMP085_CAL_MB 0xBA // R Calibration data (16 bits) 40 | #define BMP085_CAL_MC 0xBC // R Calibration data (16 bits) 41 | #define BMP085_CAL_MD 0xBE // R Calibration data (16 bits) 42 | 43 | #define BMP085_CONTROL 0xF4 44 | #define BMP085_TEMPDATA 0xF6 45 | #define BMP085_PRESSUREDATA 0xF6 46 | #define BMP085_READTEMPCMD 0x2E 47 | #define BMP085_READPRESSURECMD 0x34 48 | 49 | 50 | class ZUNO_BMP180 { 51 | public: 52 | ZUNO_BMP180(); 53 | boolean begin(uint8_t mode = BMP085_ULTRAHIGHRES); // by default go highres 54 | int16_t readTemperatureC10(void); 55 | float readTemperature(void); 56 | int32_t readPressure(void); 57 | float readAltitude(float sealevelPressure = 101325); // std atmosphere 58 | uint16_t readRawTemperature(void); 59 | uint32_t readRawPressure(void); 60 | void dumpInternal(); 61 | 62 | private: 63 | uint8_t read8(uint8_t addr); 64 | uint16_t read16(uint8_t addr); 65 | void write8(uint8_t addr, uint8_t data); 66 | 67 | uint8_t oversampling; 68 | 69 | int16_t ac1, ac2, ac3, b1, b2, mb, mc, md; 70 | uint16_t ac4, ac5, ac6; 71 | }; 72 | 73 | 74 | #endif // ADAFRUIT_BMP085_H 75 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/platform.txt: -------------------------------------------------------------------------------- 1 | 2 | # ZUNO Core and platform. 3 | # ------------------------------ 4 | 5 | # For more info: 6 | # https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5---3rd-party-Hardware-specification 7 | 8 | name=Z-Wave>ME Z-Uno Boards 9 | 10 | # ZUNO compile variables 11 | # --------------------- 12 | compiler.sdccOptions='-mmcs51 --out-fmt-ihx --model-large --verbose --debug --use-stdout --code-loc 0x8000 --xram-loc 0x3000' 13 | 14 | compiler.app=compiler 15 | compiler.app.windows=compiler.exe 16 | 17 | compiler.sdccPath={runtime.tools.zuno_toolchain.path}/zuno_toolchain/sdcc/bin/ 18 | tools.zprog.cmd.path={runtime.tools.zuno_toolchain.path}/zuno_toolchain/compiler 19 | tools.zprog.cmd.path.windows={runtime.tools.zuno_toolchain.path}/zuno_toolchain/compiler.exe 20 | 21 | tools.zprog.upload.pattern="{cmd.path}" prog "{build.path}/{build.project_name}" -d {serial.port} -fr {build.rf_freq} --param "sec={build.security}" 22 | 23 | # Default "compiler.path" is correct, change only if you want to overidde the initial value 24 | compiler.path={runtime.tools.zuno_toolchain.path}/zuno_toolchain/ 25 | 26 | # ZUNO compile patterns 27 | # -------------------- 28 | 29 | recipe.hooks.sketch.prebuild.1.pattern = {runtime.tools.zuno_toolchain.path}/zuno_toolchain/compiler build "{build.path}/{build.project_name}" -r "{runtime.platform.path}" 30 | 31 | recipe.c.o.pattern= 32 | recipe.cpp.o.pattern= 33 | recipe.S.o.pattern= 34 | recipe.ar.pattern= 35 | recipe.c.combine.pattern= 36 | recipe.objcopy.eep.pattern= 37 | recipe.objcopy.hex.pattern= 38 | 39 | ## Compute size 40 | 41 | recipe.size.pattern={runtime.tools.zuno_toolchain.path}/zuno_toolchain/compiler size "{build.path}/{build.project_name}" 42 | recipe.size.regex=^(?:rom:)\s+([0-9]+).* 43 | recipe.size.regex.data=^(?:ram:)\s+([0-9]+).* 44 | recipe.size.regex.eeprom=^(?:ram:)\s+([0-9]+).* 45 | 46 | # ZUNO Uploader/Programmers tools 47 | # ------------------------------ 48 | tools.zprog.config.path= 49 | 50 | upload.params.verbose= 51 | tools.zprog.upload.params.verbose=-v 52 | tools.zprog.upload.params.quiet=-q 53 | 54 | tools.zprog.program.params.verbose=-v 55 | tools.zprog.program.params.quiet=-q 56 | tools.zprog.program.pattern= 57 | 58 | tools.zprog.erase.params.verbose=-v 59 | tools.zprog.erase.params.quiet=-q -q 60 | tools.zprog.erase.pattern="{cmd.path}" erase -d {serial.port} 61 | 62 | tools.zprog.bootloader.params.verbose=-v 63 | tools.zprog.bootloader.params.quiet=-q 64 | tools.zprog.bootloader.pattern="{cmd.path}" boot -p "{runtime.platform.path}/bootloaders/" -d {serial.port} 65 | 66 | 67 | # USB Default Flags 68 | # Default blank usb manufacturer will be filled it at compile time 69 | # - from numeric vendor ID, set to Unknown otherwise 70 | build.usb_manufacturer="Unknown" 71 | build.usb_flags=-DUSB_VID={build.vid} -DUSB_PID={build.pid} '-DUSB_MANUFACTURER={build.usb_manufacturer}' '-DUSB_PRODUCT={build.usb_product}' 72 | 73 | 74 | 75 | 76 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/SPI.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2010 by Cristian Maglie 3 | * Copyright (c) 2014 by Paul Stoffregen (Transaction API) 4 | * Copyright (c) 2014 by Matthijs Kooijman (SPISettings AVR) 5 | * Copyright (c) 2014 by Andrew J. Kroll (atomicity fixes) 6 | * Copyright (c) 2016 by Z-Wave>ME info@z-wave.me 7 | * SPI Master library for arduino. 8 | * 9 | * This file is free software; you can redistribute it and/or modify 10 | * it under the terms of either the GNU General Public License version 2 11 | * or the GNU Lesser General Public License version 2.1, both as 12 | * published by the Free Software Foundation. 13 | * 14 | * Adoptated for Z-Uno project. 15 | */ 16 | #pragma once 17 | 18 | #include "ArduinoTypes.h" 19 | #include "ZUNO_Definitions.h" 20 | 21 | // SPI_HAS_TRANSACTION means SPI has beginTransaction(), endTransaction(), 22 | // usingInterrupt(), and SPISetting(clock, bitOrder, dataMode) 23 | #define SPI_HAS_TRANSACTION 1 24 | 25 | // SPI_HAS_NOTUSINGINTERRUPT means that SPI has notUsingInterrupt() method 26 | #define SPI_HAS_NOTUSINGINTERRUPT 1 27 | 28 | // SPI_ATOMIC_VERSION means that SPI has atomicity fixes and what version. 29 | // This way when there is a bug fix you can check this define to alert users 30 | // of your code if it uses better version of this library. 31 | // This also implies everything that SPI_HAS_TRANSACTION as documented above is 32 | // available too. 33 | #define SPI_ATOMIC_VERSION 1 34 | 35 | // Uncomment this line to add detection of mismatched begin/end transactions. 36 | // A mismatch occurs if other libraries fail to use SPI.endTransaction() for 37 | // each SPI.beginTransaction(). Connect an LED to this pin. The LED will turn 38 | // on if any mismatch is ever detected. 39 | //#define SPI_TRANSACTION_MISMATCH_LED 5 40 | 41 | 42 | class SPISettings { 43 | public: 44 | SPISettings(uint32_t clock, uint8_t bitOrder, uint8_t dataMode) { 45 | init_it(clock, bitOrder, dataMode); 46 | } 47 | SPISettings() { 48 | init_it(4000000, MSBFIRST, SPI_MODE0); 49 | } 50 | 51 | uint8_t getClock(){return m_clock;}; 52 | uint8_t getBitOrder(){return m_bitorder;}; 53 | uint8_t getMode(){return m_mode;}; 54 | 55 | 56 | 57 | private: 58 | void init_it(uint32_t clock, uint8_t bitOrder, uint8_t dataMode); 59 | 60 | uint8_t m_clock; 61 | uint8_t m_bitorder; 62 | uint8_t m_mode; 63 | 64 | }; 65 | 66 | 67 | class SPIClass { 68 | public: 69 | SPIClass(uint8_t begin_func_vec); 70 | // Initialize the SPI library 71 | void begin(); 72 | void beginTransaction(SPISettings * settings); 73 | // Write to the SPI bus (MOSI pin) and also receive (MISO pin) 74 | uint8_t transfer(uint8_t data); 75 | uint16_t transfer16(uint16_t data); 76 | void transfer(void *buf, size_t count); 77 | // After performing a group of transfers and releasing the chip select 78 | // signal, this function allows others to access the SPI bus 79 | void endTransaction(void); 80 | // Disable the SPI bus 81 | void end(); 82 | 83 | private: 84 | uint8_t begin_func_vec; 85 | uint8_t data_tmp; 86 | 87 | }; 88 | 89 | #define SPI SPI0 90 | extern SPIClass SPI0; 91 | 92 | 93 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/stdio.h: -------------------------------------------------------------------------------- 1 | /*------------------------------------------------------------------------- 2 | stdio.h - ANSI functions forward declarations 3 | 4 | Copyright (C) 1998, Sandeep Dutta . sandeep.dutta@usa.net 5 | 6 | This library is free software; you can redistribute it and/or modify it 7 | under the terms of the GNU General Public License as published by the 8 | Free Software Foundation; either version 2, or (at your option) any 9 | later version. 10 | 11 | This library is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this library; see the file COPYING. If not, write to the 18 | Free Software Foundation, 51 Franklin Street, Fifth Floor, Boston, 19 | MA 02110-1301, USA. 20 | 21 | As a special exception, if you link this library with other files, 22 | some of which are compiled with SDCC, to produce an executable, 23 | this library does not by itself cause the resulting executable to 24 | be covered by the GNU General Public License. This exception does 25 | not however invalidate any other reasons why the executable file 26 | might be covered by the GNU General Public License. 27 | -------------------------------------------------------------------------*/ 28 | 29 | #ifndef __SDC51_STDIO_H 30 | #define __SDC51_STDIO_H 1 31 | 32 | #include 33 | 34 | #ifdef __ds390 35 | #include 36 | #endif 37 | 38 | #include 39 | 40 | #ifndef EOF 41 | #define EOF (-1) 42 | #endif 43 | 44 | #ifndef NULL 45 | #define NULL (void *)0 46 | #endif 47 | 48 | #ifndef __SIZE_T_DEFINED 49 | #define __SIZE_T_DEFINED 50 | typedef unsigned int size_t; 51 | #endif 52 | 53 | /* Bounds-checking interfaces from annex K of the C11 standard. */ 54 | #if defined (__STDC_WANT_LIB_EXT1__) && __STDC_WANT_LIB_EXT1__ 55 | 56 | #ifndef __RSIZE_T_DEFINED 57 | #define __RSIZE_T_DEFINED 58 | typedef size_t rsize_t; 59 | #endif 60 | 61 | #ifndef __ERRNO_T_DEFINED 62 | #define __ERRNO_T_DEFINED 63 | typedef int errno_t; 64 | #endif 65 | 66 | #endif 67 | 68 | typedef void (*pfn_outputchar)(char c, void* p) _REENTRANT; 69 | 70 | extern int _print_format (pfn_outputchar pfn, void* pvoid, const char *format, va_list ap); 71 | 72 | /*-----------------------------------------------------------------------*/ 73 | 74 | extern void printf_small (char *,...) _REENTRANT; 75 | extern int printf (const char *,...); 76 | extern int vprintf (const char *, va_list); 77 | extern int sprintf (char *, const char *, ...); 78 | extern int vsprintf (char *, const char *, va_list); 79 | extern int puts(const char *); 80 | 81 | #if __STDC_VERSION__ < 201112L 82 | extern char *gets(char *); 83 | #endif 84 | 85 | extern char getchar(void); 86 | extern void putchar(char); 87 | 88 | #if defined(__SDCC_mcs51) && !defined(__SDCC_USE_XSTACK) 89 | extern void printf_fast(__code const char *fmt, ...) _REENTRANT; 90 | extern void printf_fast_f(__code const char *fmt, ...) _REENTRANT; 91 | extern void printf_tiny(__code const char *fmt, ...) _REENTRANT; 92 | #endif 93 | 94 | #endif /* __SDC51_STDIO_H */ 95 | -------------------------------------------------------------------------------- /hardware/examples/IRScanner/IRScanner.ino: -------------------------------------------------------------------------------- 1 | /* 2 | * Receives data from built-in IR-controller of Z-Uno and 3 | * tries to detect command and vendor 4 | * (c) Z-Wave.Me 2016 5 | */ 6 | 7 | 8 | #include 9 | 10 | // You have to connect your IR-receiver to PIN#7 of your Z-Uno 11 | // In most cases receiver ICs have built-in demodulator. 12 | // If you have one of them, please check that your receiver frequency 13 | // and fraquency of your IR-controller matches. 14 | // The most popular is 38 KHz. SAMSUNG/NEC/LG/... 15 | // SONY uses 40KHz, but in most cases its commands can be detected on 38KHz too. 16 | 17 | 18 | // Traditionally IR-receivers like VISHAY TSOP31238/TSOP312* 19 | // have inverted output. 20 | // It means that received MARK has LOW level and 21 | // SPACE has HIGH level. 22 | 23 | IRReceiverParams ir_receiver(IR_FLAGS_IO_INVERTED); 24 | IRCommand_t ir_cmd; 25 | 26 | 27 | 28 | // LED pin number 29 | #define LED_PIN 13 30 | 31 | #define MY_SERIAL Serial0 32 | 33 | 34 | 35 | void setup() { 36 | 37 | pinMode(LED_PIN, OUTPUT); // set LED pin as output 38 | digitalWrite(LED_PIN, LOW); 39 | 40 | MY_SERIAL.begin(115200); 41 | 42 | MY_SERIAL.println("\n **** Sketch is starting... ****\n"); 43 | 44 | // Setup IR-controller as receiver 45 | IR.begin(&ir_receiver); 46 | IR.scan(); 47 | 48 | 49 | 50 | } 51 | 52 | byte ir_state; 53 | word raw_data[200]; 54 | 55 | 56 | void loop() { 57 | 58 | // Check state of IR-controller 59 | ir_state = IR.getState(); 60 | 61 | if(!(ir_state & IR_STATUS_BUSY)) 62 | { 63 | 64 | 65 | // IR-Controller received a data 66 | digitalWrite(LED_PIN, HIGH); 67 | 68 | byte i; 69 | 70 | // Extract data in RAW16 format 71 | // see IRController.h for detailed descriptions 72 | IR.recv_raw16(raw_data); 73 | 74 | MY_SERIAL.print("RAW16_data["); 75 | MY_SERIAL.print(raw_data[0]+1); 76 | MY_SERIAL.print("]= {"); 77 | // Length of packet stored in the first word 78 | for(i=0;i<=raw_data[0];i++) 79 | { 80 | if(i != 0) 81 | MY_SERIAL.print(", "); 82 | MY_SERIAL.print("0x"); 83 | MY_SERIAL.print(raw_data[i], HEX); 84 | 85 | } 86 | MY_SERIAL.println("}"); 87 | 88 | // In some cases we can decode command 89 | // from MARK/SPACES to binary code and 90 | // now we will try it... 91 | MY_SERIAL.println("Trying to decode command: "); 92 | if(IR.detectCommand(&ir_cmd)) 93 | { 94 | MY_SERIAL.print("Vendor: "); 95 | MY_SERIAL.print(ir_cmd.vendor); 96 | MY_SERIAL.print(" Bits: "); 97 | MY_SERIAL.print(ir_cmd.n_bits); 98 | // For some protocols commands have 99 | // 64 bit length 100 | if(ir_cmd.n_bits > 32) 101 | { 102 | MY_SERIAL.print(" Command: \n HW:"); 103 | MY_SERIAL.print(ir_cmd.data[0], HEX); 104 | MY_SERIAL.print(" LW:"); 105 | MY_SERIAL.println(ir_cmd.data[1], HEX); 106 | } 107 | else 108 | { 109 | MY_SERIAL.print(" Command: "); 110 | MY_SERIAL.println(ir_cmd.data[0], HEX); 111 | } 112 | 113 | } 114 | 115 | // restart scan process 116 | IR.scan(); 117 | digitalWrite(LED_PIN, LOW); 118 | } 119 | 120 | 121 | delay(500); 122 | 123 | 124 | 125 | } 126 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZMEKeypad/ZMEKeypad.cpp: -------------------------------------------------------------------------------- 1 | #include "ZMEKeypad.h" 2 | 3 | 4 | ZMEKeypad::ZMEKeypad(BYTE * colums, BYTE numcols, BYTE * rows, BYTE numrows) 5 | { 6 | column_vec = colums; 7 | n_col = numcols; 8 | row_vec = rows; 9 | n_row = numrows; 10 | mon_keys = 0; 11 | 12 | hold_time = HOLD_DEFAULT_TIME; 13 | debounce_time = DEBOUNCE_DEFAULT_TIME; 14 | 15 | 16 | } 17 | 18 | void ZMEKeypad::begin() 19 | { 20 | BYTE i; 21 | 22 | for (i=0; i debounce_time) 70 | key_states[mon_key_index].key_state = KEYPAD_KEYSTATE_PRESSED; 71 | break; 72 | case KEYPAD_KEYSTATE_PRESSED: 73 | if(kt > hold_time) 74 | key_states[mon_key_index].key_state = KEYPAD_KEYSTATE_HOLDED; 75 | break; 76 | case KEYPAD_KEYSTATE_HOLDED: 77 | key_actions[ret] = key_num | 0x80; 78 | ret++; 79 | break; 80 | } 81 | } 82 | else 83 | { 84 | if(mon_keys >= MAX_SCAN_KEYS) 85 | break; 86 | // Add this key to keypad state, return to the start condition 87 | key_states[mon_keys].key_num = key_num; 88 | key_states[mon_keys].key_state = KEYPAD_KEYSTATE_DEBOUNCE; 89 | key_states[mon_keys].time = scan_time; 90 | mon_keys++; 91 | } 92 | 93 | 94 | } 95 | else 96 | { 97 | if(mon_key_index != 0xFF) 98 | { 99 | if(key_states[mon_key_index].key_state == KEYPAD_KEYSTATE_PRESSED) 100 | { 101 | key_actions[ret] = key_num; 102 | ret++; 103 | } 104 | 105 | // Remove key from list 106 | for(i=mon_key_index;i<(mon_keys-1);i++) 107 | { 108 | key_states[i].key_num = key_states[i+1].key_num; 109 | key_states[i].key_state = key_states[i+1].key_state; 110 | key_states[i].time = key_states[i+1].time; 111 | } 112 | mon_keys--; 113 | } 114 | 115 | 116 | } 117 | 118 | } 119 | m_pinSet(column_vec[c], HIGH); // Begin column pulse output. 120 | 121 | } 122 | 123 | return ret; 124 | 125 | } 126 | 127 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/LLCore_arduino.h: -------------------------------------------------------------------------------- 1 | #ifndef CORE_ARDUINO_ZUNO__ 2 | #define CORE_ARDUINO_ZUNO__ 3 | 4 | #include "ArduinoTypes.h" 5 | #include "ZUNO_Definitions.h" 6 | 7 | typedef __code void (*VOID_FUNC_POINTER_VOID) (void); 8 | typedef __code void (*VOID_FUNC_POINTER_BYTE) (BYTE value); 9 | typedef __code void (*VOID_FUNC_POINTER_DW0RD) (DWORD value); 10 | typedef __code BYTE (*BYTE_FUNC_POINTER_VOID) (void); 11 | typedef __code WORD (*WORD_FUNC_POINTER_VOID) (void); 12 | typedef __code DWORD (*DWORD_FUNC_POINTER_VOID) (void); 13 | typedef __code void (*VOID_FUNC_POINTER_BUFFER) (const char *bufPointer); 14 | typedef __code void (*VOID_FUNC_POINTER_BUFFER_BYTE) (const char *bufPointer, BYTE value); 15 | typedef __code void * GENERIC_POINTER; 16 | 17 | 18 | 19 | 20 | //Debug/// 21 | BYTE zunoPopByte(void); 22 | WORD zunoPopWord(void); 23 | DWORD zunoPopDWORD(void); 24 | void zunoPushByte(BYTE value); 25 | void zunoPushWord(WORD value); 26 | void zunoPushDword(DWORD value); 27 | void zunoCall(void); 28 | //******************************** 29 | void pinMode(BYTE pin, BYTE mode); 30 | BYTE digitalRead(BYTE pin); 31 | void digitalWrite(BYTE pin, BYTE value); 32 | void delay(DWORD value); 33 | WORD analogRead(BYTE pin); 34 | void analogWrite(BYTE pin, BYTE value); 35 | //********************************************** 36 | void setup(void); 37 | void loop(void); 38 | void InitArduinoEnvironment(void); 39 | 40 | BYTE zme_strlen(char * str); 41 | 42 | 43 | // System Datatypes 44 | // ----------------------------------------------------------------- 45 | typedef struct _ZUNO_CHANNEL_PROPERTIES_DESCRIPTION 46 | { 47 | BYTE channel_cmd_class; 48 | BYTE channel_sensor_type; 49 | BYTE channel_multilevel_properties; 50 | GENERIC_POINTER getter; 51 | GENERIC_POINTER setter; 52 | } ZUNO_CHANNEL_PROPERTIES_DESCRIPTION; 53 | 54 | 55 | typedef struct _ZUNO_ASSOCIATION_PROPERTIES_DESCRIPTION 56 | { 57 | BYTE association_type; 58 | BYTE association_param; 59 | } ZUNO_ASSOCIATION_PROPERTIES_DESCRIPTION; 60 | 61 | typedef struct _ZUNO_SLEEPING_MODE_PROPERTIES_DESCRIPTION 62 | { 63 | BYTE current_mode; 64 | BYTE parameter; 65 | GENERIC_POINTER handler; 66 | } ZUNO_SLEEPING_MODE_PROPERTIES_DESCRIPTION; 67 | // ----------------------------------------------------------------- 68 | 69 | #define ZUNO_SETUP_CHANNELS(...) \ 70 | __code ZUNO_CHANNEL_PROPERTIES_DESCRIPTION zunoChannelSetupArray[]= \ 71 | { \ 72 | {0x42, 0x42, 0x42, 0x4242, 0x4242}, \ 73 | __VA_ARGS__, \ 74 | {0x43, 0x43, 0x43, 0x4343, 0x4343} \ 75 | } 76 | // !! remove 77 | // Reverse compatibility 78 | // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 79 | #define ZUNO_SETUP_FREQUENCY(VALUE) BYTE ___dummy_freq 80 | // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 81 | 82 | #define ZUNO_SETUP_DEBUG_MODE(VALUE) \ 83 | __code BYTE zunoDebugParameter = VALUE 84 | // System externs 85 | // ----------------------------------------------------------------- 86 | extern __code ZUNO_CHANNEL_PROPERTIES_DESCRIPTION zunoChannelSetupArray[]; 87 | extern __code ZUNO_ASSOCIATION_PROPERTIES_DESCRIPTION zunoAssociationSetupArray[]; 88 | extern __code ZUNO_SLEEPING_MODE_PROPERTIES_DESCRIPTION zunoSleepingModeSetupStruct; 89 | extern __code BYTE zunoDebugParameter; 90 | // ----------------------------------------------------------------- 91 | 92 | 93 | /************************************************ 94 | end of Variables 95 | ************************************************/ 96 | 97 | 98 | #endif // CORE_ARDUINO_ZUNO__ 99 | 100 | 101 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/math.h: -------------------------------------------------------------------------------- 1 | /*------------------------------------------------------------------------- 2 | math.h: Floating point math function declarations 3 | 4 | Copyright (C) 2001, Jesus Calvino-Fraga, jesusc@ieee.org 5 | 6 | This library is free software; you can redistribute it and/or modify it 7 | under the terms of the GNU General Public License as published by the 8 | Free Software Foundation; either version 2, or (at your option) any 9 | later version. 10 | 11 | This library is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this library; see the file COPYING. If not, write to the 18 | Free Software Foundation, 51 Franklin Street, Fifth Floor, Boston, 19 | MA 02110-1301, USA. 20 | 21 | As a special exception, if you link this library with other files, 22 | some of which are compiled with SDCC, to produce an executable, 23 | this library does not by itself cause the resulting executable to 24 | be covered by the GNU General Public License. This exception does 25 | not however invalidate any other reasons why the executable file 26 | might be covered by the GNU General Public License. 27 | -------------------------------------------------------------------------*/ 28 | 29 | /* Version 1.0 - Initial release */ 30 | 31 | #ifndef _INC_MATH 32 | #define _INC_MATH 33 | 34 | #define HUGE_VALF 3.402823466e+38 35 | 36 | #define PI 3.1415926536 37 | #define TWO_PI 6.2831853071 38 | #define HALF_PI 1.5707963268 39 | #define QUART_PI 0.7853981634 40 | #define iPI 0.3183098862 41 | #define iTWO_PI 0.1591549431 42 | #define TWO_O_PI 0.6366197724 43 | 44 | /* EPS=B**(-t/2), where B is the radix of the floating-point representation 45 | and there are t base-B digits in the significand. Therefore, for floats 46 | EPS=2**(-12). Also define EPS2=EPS*EPS. */ 47 | #define EPS 244.14062E-6 48 | #define EPS2 59.6046E-9 49 | 50 | union float_long 51 | { 52 | float f; 53 | long l; 54 | }; 55 | 56 | 57 | 58 | 59 | /* Functions on the z80 & gbz80 are always reentrant and so the "reentrant" */ 60 | /* keyword is not defined. */ 61 | 62 | #define _FLOAT_FUNC_REENTRANT //__reentrant 63 | 64 | 65 | /********************************************** 66 | * Prototypes for float ANSI C math functions * 67 | **********************************************/ 68 | 69 | /* Trigonometric functions */ 70 | float sinf(float x) _FLOAT_FUNC_REENTRANT; 71 | float cosf(float x) _FLOAT_FUNC_REENTRANT; 72 | float tanf(float x) _FLOAT_FUNC_REENTRANT; 73 | float cotf(float x) _FLOAT_FUNC_REENTRANT; 74 | float asinf(float x) _FLOAT_FUNC_REENTRANT; 75 | float acosf(float x) _FLOAT_FUNC_REENTRANT; 76 | float atanf(float x) _FLOAT_FUNC_REENTRANT; 77 | float atan2f(float x, float y); 78 | 79 | /* Hyperbolic functions */ 80 | float sinhf(float x) _FLOAT_FUNC_REENTRANT; 81 | float coshf(float x) _FLOAT_FUNC_REENTRANT; 82 | float tanhf(float x) _FLOAT_FUNC_REENTRANT; 83 | 84 | /* Exponential, logarithmic and power functions */ 85 | float expf(float x) _FLOAT_FUNC_REENTRANT; 86 | float logf(float x) _FLOAT_FUNC_REENTRANT; 87 | float log10f(float x) _FLOAT_FUNC_REENTRANT; 88 | float powf(float x, float y); 89 | float sqrtf(float a) _FLOAT_FUNC_REENTRANT; 90 | 91 | /* Nearest integer, absolute value, and remainder functions */ 92 | float fabsf(float x) _FLOAT_FUNC_REENTRANT; 93 | float frexpf(float x, int *pw2); 94 | float ldexpf(float x, int pw2); 95 | float ceilf(float x) _FLOAT_FUNC_REENTRANT; 96 | float floorf(float x) _FLOAT_FUNC_REENTRANT; 97 | float modff(float x, float * y); 98 | 99 | #endif /* _INC_MATH */ 100 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/SPI.cpp: -------------------------------------------------------------------------------- 1 | #include "SPI.h" 2 | 3 | #include "ZUNO_Definitions.h" 4 | #include "ZUNO_call_proto.h" 5 | 6 | #define SPI_BEGIN_FUNC_VEC(n) (n + 0) 7 | #define SPI_ENABLE_FUNC_VEC(n) (n + 1) 8 | #define SPI_TRANSFER_FUNC_VEC(n) (n + 2) 9 | 10 | 11 | void SPISettings::init_it(uint32_t clock, uint8_t bitOrder, uint8_t dataMode){ 12 | // Clock settings are defined as follows. Note that this shows SPI2X 13 | // inverted, so the bits form increasing numbers. Also note that 14 | // fosc/64 appears twice 15 | // SPR1 SPR0 ~SPI2X Freq 16 | // 0 0 0 fosc/2 17 | // 0 0 1 fosc/4 18 | // 0 1 0 fosc/8 19 | // 0 1 1 fosc/16 20 | // 1 0 0 fosc/32 21 | // 1 0 1 fosc/64 22 | // 1 1 0 fosc/64 23 | // 1 1 1 fosc/128 24 | 25 | // We find the fastest clock that is less than or equal to the 26 | // given clock rate. The clock divider that results in clock_setting 27 | // is 2 ^^ (clock_div + 1). If nothing is slow enough, we'll use the 28 | // slowest (128 == 2 ^^ 7, so clock_div = 6). 29 | uint8_t clockDiv; 30 | uint32_t clockSetting = F_CPU / 2; 31 | clockDiv = 0; 32 | while (clockDiv < 6 && clock < clockSetting) { 33 | clockSetting /= 2; 34 | clockDiv++; 35 | } 36 | 37 | 38 | // Compensate for the duplicate fosc/64 39 | if (clockDiv == 6) 40 | clockDiv = 7; 41 | 42 | m_clock = clockDiv; 43 | m_bitorder = bitOrder; 44 | m_mode = dataMode; 45 | 46 | } 47 | 48 | // Initialize the SPI library 49 | SPIClass::SPIClass(uint8_t begin_func_vec) 50 | { 51 | this->begin_func_vec = begin_func_vec; 52 | } 53 | void SPIClass::begin() 54 | { 55 | 56 | } 57 | void SPIClass::beginTransaction(SPISettings * settings) 58 | { 59 | 60 | 61 | uint8_t speed = settings->getClock(); 62 | uint8_t mode = settings->getMode(); 63 | uint8_t border = settings->getBitOrder(); 64 | 65 | 66 | if ( (speed > SPI_SPEED_1_MHZ) || (mode > SPI_MODE3) || (border > MSBFIRST)) { 67 | // unsupported values 68 | return; 69 | } 70 | 71 | zunoPushByte(speed | (mode << 2) | (border << 4)); 72 | zunoPushByte(SPI_BEGIN_FUNC_VEC(begin_func_vec)); 73 | zunoCall(); 74 | 75 | zunoPushByte(TRUE); 76 | zunoPushByte(SPI_ENABLE_FUNC_VEC(begin_func_vec)); 77 | zunoCall(); 78 | 79 | } 80 | uint8_t SPIClass::transfer(uint8_t data) 81 | { 82 | uint8_t ret; 83 | 84 | data_tmp = data; 85 | 86 | zunoPushWord(reinterpPOINTER(&data_tmp)); 87 | zunoPushByte(1); 88 | zunoPushByte(SPI_TRANSFER_FUNC_VEC(begin_func_vec)); 89 | zunoCall(); 90 | 91 | return data_tmp; 92 | } 93 | uint16_t SPIClass::transfer16(uint16_t data) 94 | { 95 | uint8_t in_out[2]; 96 | uint8_t i; 97 | WORD result =0; 98 | 99 | in_out[0] = data >> 8; 100 | in_out[1] = data & 0xFF; 101 | 102 | zunoPushWord(reinterpPOINTER(in_out)); 103 | zunoPushByte(2); 104 | zunoPushByte(SPI_TRANSFER_FUNC_VEC(begin_func_vec)); 105 | zunoCall(); 106 | 107 | result = in_out[0]; 108 | result <<= 8; 109 | result += in_out[1]; 110 | 111 | return result; 112 | 113 | } 114 | void SPIClass::transfer(void *buf, size_t count) 115 | { 116 | zunoPushWord(reinterpPOINTER((BYTE*)buf)); 117 | zunoPushByte(count); 118 | zunoPushByte(SPI_TRANSFER_FUNC_VEC(begin_func_vec)); 119 | zunoCall(); 120 | 121 | } 122 | void SPIClass::endTransaction(void) 123 | { 124 | zunoPushByte(FALSE); 125 | zunoPushByte(SPI_ENABLE_FUNC_VEC(begin_func_vec)); 126 | zunoCall(); 127 | 128 | } 129 | void SPIClass::end() 130 | { 131 | zunoPushByte(FALSE); 132 | zunoPushByte(SPI_ENABLE_FUNC_VEC(begin_func_vec)); 133 | zunoCall(); 134 | } 135 | // Глобальная переменнная для SPI0 136 | SPIClass SPI0(ZUNO_FUNC_SPI0_INIT); 137 | 138 | 139 | 140 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_DS18B20/ZUNO_DS18B20.cpp: -------------------------------------------------------------------------------- 1 | #include "ZUNO_DS18B20.h" 2 | #define DS18B20FAMILY 0x28 3 | 4 | #define DEBUG_TEMP_CONV 0 5 | DS18B20Sensor::DS18B20Sensor(OneWire * ow): 6 | my_ow(ow), 7 | current_delay(75) // in 10th of microseconds == 750ms 8 | { 9 | 10 | } 11 | byte DS18B20Sensor::scanAloneSensor(byte * rom) 12 | { 13 | if(!my_ow->reset()) 14 | return 0; 15 | my_ow->readROM(rom); 16 | if(rom[7] != my_ow->crc8(rom,7)) 17 | return 0; 18 | return 1; 19 | } 20 | 21 | 22 | byte DS18B20Sensor::findAllSensors(byte * rom) 23 | { 24 | byte count = 0; 25 | my_ow->reset_search(); 26 | while(my_ow->search(rom)) 27 | { 28 | // Check that CRC is valid 29 | if(rom[7] != my_ow->crc8(rom,7)) 30 | continue; 31 | // Check that it's a ds18b20 sensor 32 | if(rom[0] != DS18B20FAMILY) 33 | continue; 34 | rom += 8; 35 | count++; 36 | } 37 | 38 | return count; 39 | 40 | } 41 | void DS18B20Sensor::setResolution(byte res, byte * addr) 42 | { 43 | if (!my_ow->reset()) 44 | return; 45 | 46 | if(addr) 47 | my_ow->select(addr); 48 | else 49 | my_ow->skip(); 50 | 51 | // Write scratchpad 52 | my_ow->write(0x4E); 53 | // Default TH/TL 54 | my_ow->write(0x4B); 55 | my_ow->write(0x46); 56 | // Control reg 57 | my_ow->write((res << 5) | 0x1F); 58 | 59 | if (!my_ow->reset()) 60 | return; 61 | 62 | if(addr) 63 | my_ow->select(addr); 64 | else 65 | my_ow->skip(); 66 | // Copy scratchpad 67 | my_ow->write(0x48); 68 | delay(10); 69 | if (!my_ow->reset()) 70 | return; 71 | 72 | 73 | 74 | } 75 | int DS18B20Sensor::getTempC100(byte * addr) 76 | { 77 | int temp = BAD_TEMP; 78 | byte dallas_data[9]; 79 | byte i; 80 | 81 | if (!my_ow->reset()) 82 | return temp; 83 | 84 | if(addr) 85 | my_ow->select(addr); 86 | else 87 | my_ow->skip(); 88 | 89 | my_ow->write(0x44); 90 | 91 | #if DEBUG_TEMP_CONV 92 | Serial0.print( " Current delay:"); 93 | Serial0.print(current_delay); 94 | Serial0.print( " Current resolution:"); 95 | Serial0.print(current_resolution); 96 | #endif 97 | 98 | delay(int(current_delay*10)); 99 | 100 | if(!my_ow->reset()) 101 | return temp; 102 | 103 | if(addr) 104 | my_ow->select(addr); 105 | else 106 | my_ow->skip(); 107 | 108 | my_ow->write(0xBE); // Read Scratchpad 109 | 110 | #if DEBUG_TEMP_CONV 111 | Serial0.print( " RAW:{ "); 112 | #endif 113 | 114 | for ( i = 0; i < 9; i++) 115 | { 116 | // we need 9 bytes 117 | dallas_data[i] = my_ow->read(); 118 | #if DEBUG_TEMP_CONV 119 | Serial0.print(dallas_data[i], HEX); 120 | Serial0.print(" "); 121 | #endif 122 | } 123 | #if DEBUG_TEMP_CONV 124 | Serial0.println("}"); 125 | #endif 126 | 127 | temp = dallas_data[1] & 0x07; // For all other bits we have 1 when temperature < 0 128 | temp <<= 8; 129 | temp |= dallas_data[0]; 130 | 131 | // extract current resolution from control register 132 | current_resolution = (dallas_data[4] >> 5) & 0x03; 133 | // current_delay ~ 10*2^resolution 134 | current_delay = 10; 135 | current_delay <<= current_resolution; 136 | // fill low bits with zeros 137 | // using current resolution 138 | temp &= ~((1 << (3 - current_resolution))-1); 139 | 140 | // We use fixed point calculations here 141 | // so the following sequence 142 | // temp /= 0.16 143 | // will be 144 | // 16/100 => 4/25 => temp *= 25; tem/=4; 145 | temp *= 25; 146 | temp >>= 2; 147 | 148 | // Fix sign of value 149 | if(dallas_data[1] & 0x80) 150 | temp = -temp; 151 | 152 | 153 | 154 | return temp; 155 | } 156 | 157 | float DS18B20Sensor::getTemperature(byte * addr) 158 | { 159 | return getTempC100(addr) / 100.0; 160 | 161 | } -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_OLED_I2C/ZUNO_OLED_I2C.h: -------------------------------------------------------------------------------- 1 | /* 2 | **************************************************************************** 3 | **************************************************************************** 4 | */ 5 | 6 | /* 7 | OLED_I2C.h - Arduino/chipKit library support for 128x64 pixel SSD1306 OLEDs 8 | Copyright (C)2015 Rinky-Dink Electronics, Henning Karlsen. All right reserved 9 | 10 | This library has been made to make it easy to use 128x64 pixel OLED displays 11 | based on the SSD1306 controller chip with an Arduino or a chipKit. 12 | 13 | You can always find the latest version of the library at 14 | http://www.RinkyDinkElectronics.com/ 15 | 16 | This library is free software; you can redistribute it and/or 17 | modify it under the terms of the CC BY-NC-SA 3.0 license. 18 | Please see the included documents for further information. 19 | 20 | Commercial use of this library requires you to buy a license that 21 | will allow commercial use. This includes using the library, 22 | modified or not, as a tool to sell products. 23 | 24 | The license applies to all part of the library including the 25 | examples and tools supplied with the library. 26 | 27 | Adoptated for Z-Uno project by Z-Wave>ME 2016 28 | */ 29 | 30 | #ifndef OLED_I2C_h 31 | #define OLED_I2C_h 32 | 33 | #define SSD1306_ADDR 0x3C 34 | 35 | #define LEFT 0 36 | #define RIGHT 9999 37 | #define CENTER 9998 38 | 39 | #define SSD1306_COMMAND 0x00 40 | #define SSD1306_DATA 0xC0 41 | #define SSD1306_DATA_CONTINUE 0x40 42 | 43 | #define RST_NOT_IN_USE 255 44 | 45 | // SSD1306 Commandset 46 | // ------------------ 47 | // Fundamental Commands 48 | #define SSD1306_SET_CONTRAST_CONTROL 0x81 49 | #define SSD1306_DISPLAY_ALL_ON_RESUME 0xA4 50 | #define SSD1306_DISPLAY_ALL_ON 0xA5 51 | #define SSD1306_NORMAL_DISPLAY 0xA6 52 | #define SSD1306_INVERT_DISPLAY 0xA7 53 | #define SSD1306_DISPLAY_OFF 0xAE 54 | #define SSD1306_DISPLAY_ON 0xAF 55 | #define SSD1306_NOP 0xE3 56 | // Scrolling Commands 57 | #define SSD1306_HORIZONTAL_SCROLL_RIGHT 0x26 58 | #define SSD1306_HORIZONTAL_SCROLL_LEFT 0x27 59 | #define SSD1306_HORIZONTAL_SCROLL_VERTICAL_AND_RIGHT 0x29 60 | #define SSD1306_HORIZONTAL_SCROLL_VERTICAL_AND_LEFT 0x2A 61 | #define SSD1306_DEACTIVATE_SCROLL 0x2E 62 | #define SSD1306_ACTIVATE_SCROLL 0x2F 63 | #define SSD1306_SET_VERTICAL_SCROLL_AREA 0xA3 64 | // Addressing Setting Commands 65 | #define SSD1306_SET_LOWER_COLUMN 0x00 66 | #define SSD1306_SET_HIGHER_COLUMN 0x10 67 | #define SSD1306_MEMORY_ADDR_MODE 0x20 68 | #define SSD1306_SET_COLUMN_ADDR 0x21 69 | #define SSD1306_SET_PAGE_ADDR 0x22 70 | // Hardware Configuration Commands 71 | #define SSD1306_SET_START_LINE 0x40 72 | #define SSD1306_SET_SEGMENT_REMAP 0xA0 73 | #define SSD1306_SET_MULTIPLEX_RATIO 0xA8 74 | #define SSD1306_COM_SCAN_DIR_INC 0xC0 75 | #define SSD1306_COM_SCAN_DIR_DEC 0xC8 76 | #define SSD1306_SET_DISPLAY_OFFSET 0xD3 77 | #define SSD1306_SET_COM_PINS 0xDA 78 | #define SSD1306_CHARGE_PUMP 0x8D 79 | // Timing & Driving Scheme Setting Commands 80 | #define SSD1306_SET_DISPLAY_CLOCK_DIV_RATIO 0xD5 81 | #define SSD1306_SET_PRECHARGE_PERIOD 0xD9 82 | #define SSD1306_SET_VCOM_DESELECT 0xDB 83 | 84 | 85 | #include "Arduino.h" 86 | 87 | 88 | struct _current_font 89 | { 90 | uint8_t* font; 91 | uint8_t x_size; 92 | uint8_t y_size; 93 | uint8_t offset; 94 | uint8_t numchars; 95 | uint8_t inverted; 96 | }; 97 | 98 | class OLED:public Print 99 | { 100 | public: 101 | OLED(); 102 | 103 | void begin(); 104 | void setBrightness(uint8_t value); 105 | void writeData(byte * pdata, byte p1, byte p2, byte c1, byte c2); 106 | 107 | void invert(bool mode); 108 | void clrscr(); 109 | void gotoXY(byte x, byte y); 110 | virtual size_t write(uint8_t value); 111 | private: 112 | //void sendTWIcommand(byte d); 113 | 114 | protected: 115 | byte cx,cy; 116 | 117 | 118 | 119 | }; 120 | 121 | #endif -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/HLCore.cpp: -------------------------------------------------------------------------------- 1 | #include "Arduino.h" 2 | 3 | #include "ZUNO_call_proto.h" 4 | 5 | DWORD g_pulse_timeout_us = 0; // in microseconds 6 | DWORD g_pulse_timeout_loops = 0; // in cycles == 1s 7 | 8 | 9 | // calculate micros 10 | // 11 | // time = c + cycles * f 12 | // where c & f are constants 13 | // We can calculate it by means of logic analyzer 14 | // We have at least 2 measures and make system of equaluation 15 | // 1) measured_timeout1 = c + n1 * f 16 | // 2) measured_timeout2 = c + n2 * f 17 | // Just take a table by means of logic analyzer 18 | // #loops #us 19 | // 14 80.31us 20 | // 425 2156 us 21 | // 901 4573 us 22 | // 144 738.4 us 23 | // 24 | // s1 = n1*f + c 25 | // s2 = n2*f + c 26 | // 80 = 14*f + c 27 | // 4573 = 901*f + c we have c = 4573 - 901*f 28 | // 887*f = 4493 29 | // f = 5.06538 us 30 | // c = 9.09262 us 31 | // We have to use fixed-point math. All values are in nano seconds (1e-9) 32 | 33 | #define F_CONTANT_NANOS 3069 34 | #define C_CONTANT_NANOS 3200 35 | 36 | 37 | #define LOOPS_TO_US(L) L *= F_CONTANT_NANOS; L += C_CONTANT_NANOS; L /= 1000; 38 | #define US_TO_LOOPS(U) U *= 1000; U -= C_CONTANT_NANOS; U /= F_CONTANT_NANOS; 39 | 40 | 41 | void setPulseTimeout(DWORD timeout) 42 | { 43 | 44 | g_pulse_timeout_us = timeout; 45 | 46 | US_TO_LOOPS(timeout); 47 | 48 | g_pulse_timeout_loops = timeout; 49 | } 50 | // Be careful. Don't use values < 500uS for timeout 51 | DWORD pulseIn(s_pin pin, byte level, DWORD timeout) 52 | { 53 | DWORD width = 0; 54 | //DWORD timeout; 55 | byte port_mask = 1 << (pin - 9); 56 | 57 | 58 | // If you change timeout... 59 | if(timeout != g_pulse_timeout_us) 60 | { 61 | // ... it takes about 500uS for 8051 62 | // don't do it every time 63 | setPulseTimeout(timeout); 64 | } 65 | // use precaculated value of timeout in "loops" 66 | timeout = g_pulse_timeout_loops; 67 | if(!level) 68 | port_mask = 0; 69 | 70 | 71 | noInterrupts(); 72 | // wait for any previous pulse to end 73 | while(digitalRead(pin) == port_mask) 74 | { 75 | if(!timeout) 76 | { 77 | interrupts(); 78 | return 0; 79 | } 80 | timeout--; 81 | } 82 | // wait for the pulse to start 83 | while(digitalRead(pin) != port_mask) 84 | { 85 | if(!timeout) 86 | { 87 | interrupts(); 88 | return 0; 89 | } 90 | timeout--; 91 | } 92 | 93 | width = timeout; 94 | // wait for the pulse to stop 95 | while(digitalRead(pin) == port_mask) 96 | { 97 | width--; 98 | if(!width) 99 | { 100 | interrupts(); 101 | return 0; 102 | } 103 | } 104 | interrupts(); 105 | 106 | timeout -= width; 107 | 108 | 109 | // time = c + cycles * f 110 | // see below 111 | // calculate micros 112 | 113 | LOOPS_TO_US(timeout); 114 | return timeout; 115 | } 116 | 117 | #define DELAYUS_STATIC_LOOP_CYCLES 14 118 | #define DELAYUS_STATIC_LOOP_SUB 9 119 | 120 | // The minimum delay is 9 uS 121 | // The precision is about 4 us 122 | // Function more precise for intervals 123 | // interval = 9 + n*4 124 | // 9 13 17 21 25 29 33 37 41 45 49 ... 97 ... 101 ... 16009 125 | // Any other interval will be moved to nearest low value of this raw 126 | void delayMicroseconds(word us) 127 | { 128 | NOPS(1); 129 | if(us>= 2; // every loop tuned to 4 useconds 139 | while(us--) 140 | { 141 | NOPS(DELAYUS_STATIC_LOOP_CYCLES); 142 | } 143 | } 144 | 145 | /// math 146 | long map(long x, long in_min, long in_max, long out_min, long out_max) 147 | { 148 | return (x - in_min) * (out_max - out_min) / (in_max - in_min) + out_min; 149 | } 150 | 151 | 152 | #if 0 153 | void testZunoCall() 154 | { 155 | word w1 = 0xAABB; 156 | DWORD dw1 = 0xCCDDEEF0; 157 | 158 | zunoPushDword(dw1); 159 | zunoPushWord(w1); 160 | zunoPushByte(ZUNO_FUNC_TEST); 161 | zunoCall(); 162 | 163 | w1 = zunoPopWord(); 164 | dw1 = zunoPopDWORD(); 165 | 166 | #if 1 167 | // DBG 168 | Serial0.println("TEST_FUNC Result"); 169 | Serial0.println(w1, HEX); 170 | Serial0.println(dw1, HEX); 171 | Serial0.println("----------------"); 172 | 173 | #endif 174 | 175 | } 176 | #endif -------------------------------------------------------------------------------- /hardware/examples/IR2ZWave/IR2ZWave.ino: -------------------------------------------------------------------------------- 1 | 2 | /* 3 | * Receives data from built-in IR-controller of Z-Uno and 4 | * sends command to specified group via Z-Wave 5 | * (c) Z-Wave.Me 2016 6 | */ 7 | 8 | #include 9 | 10 | // You have to connect your IR-receiver to PIN#7 of your Z-Uno 11 | // In most cases receiver ICs have built-in demodulator. 12 | // If you have one of them, please check that your receiver frequency 13 | // and fraquency of your IR-controller matches. 14 | // The most popular is 38 KHz. SAMSUNG/NEC/LG/... 15 | // SONY uses 40KHz, but in most cases its commands can be detected on 38KHz too. 16 | 17 | 18 | // Setup associations - we have 2 groups for on/off behavior 19 | ZUNO_SETUP_ASSOCIATIONS(ZUNO_ASSOCIATION_GROUP_SET_VALUE, ZUNO_ASSOCIATION_GROUP_SET_VALUE); 20 | 21 | // Traditionally IR-receivers like VISHAY TSOP31238/TSOP312* 22 | // have inverted output. 23 | // It means that received MARK has LOW level and 24 | // SPACE has HIGH level. 25 | 26 | IRReceiverParams ir_receiver(IR_FLAGS_IO_INVERTED); 27 | IRCommand_t ir_cmd; 28 | byte ir_state; 29 | word raw_data[200]; 30 | 31 | // LED pin number 32 | #define LED_PIN 13 33 | 34 | #define MY_SERIAL Serial0 35 | #define SWITCH_ON 0xff 36 | #define SWITCH_OFF 0 37 | 38 | #define CONTROL_GROUP1 1 // RAW GROUP 39 | #define CONTROL_GROUP2 2 // VENDOR GROUP 40 | 41 | // Use IRScanner.ino as IR-sniffer 42 | // Sniffed raw16 commands 43 | // This codes were shiffed from Apple IR Controller 44 | // RAW: Up/DOWN Decoded: Left/Right 45 | word raw_command_on[] = {0x43, 0x2392, 0x1171, 0x24E, 0x219, 0x249, 0x66F, 0x248, 0x66F, 0x249, 0x66F, 0x249, 0x21E, 0x24E, 0x66A, 0x24E, 0x66A, 0x24D, 0x66A, 0x24D, 0x66B, 0x24D, 0x66B, 0x24C, 0x66C, 0x24C, 0x21B, 0x246, 0x221, 0x24C, 0x21B, 0x247, 0x220, 0x24D, 0x66B, 0x24C, 0x66B, 0x24C, 0x66B, 0x24C, 0x21A, 0x247, 0x670, 0x247, 0x21F, 0x24D, 0x219, 0x248, 0x21E, 0x24F, 0x218, 0x24A, 0x21C, 0x245, 0x221, 0x24B, 0x66C, 0x24B, 0x21C, 0x246, 0x220, 0x24C, 0x21A, 0x247, 0x671, 0x246, 0x231, 0x247}; 46 | word raw_command_off[] = {0x43, 0x239C, 0x1165, 0x250, 0x231, 0x231, 0x66C, 0x24B, 0x66C, 0x24B, 0x66C, 0x24C, 0x235, 0x22C, 0x670, 0x247, 0x66F, 0x248, 0x66E, 0x249, 0x66D, 0x24A, 0x66C, 0x24B, 0x66B, 0x24D, 0x234, 0x22D, 0x239, 0x234, 0x232, 0x22F, 0x237, 0x236, 0x666, 0x247, 0x670, 0x247, 0x23A, 0x232, 0x66A, 0x24D, 0x669, 0x24E, 0x233, 0x22E, 0x238, 0x235, 0x232, 0x230, 0x236, 0x22B, 0x23B, 0x231, 0x235, 0x22D, 0x66F, 0x249, 0x238, 0x234, 0x232, 0x230, 0x236, 0x236, 0x666, 0x246, 0x24B, 0x22D}; 47 | 48 | // Detected vendor 49 | #define MY_IR_VENDOR IR_VENDOR_NEC // NEC protocol in most cases 50 | // Decoded commands 51 | #define MY_IR_VENDOR_CMD_ON 0x77E1E022 52 | #define MY_IR_VENDOR_CMD_OFF 0x77E11022 53 | 54 | 55 | void setup() { 56 | 57 | pinMode(LED_PIN, OUTPUT); // set LED pin as output 58 | digitalWrite(LED_PIN, LOW); 59 | 60 | MY_SERIAL.begin(115200); 61 | 62 | MY_SERIAL.println("\n **** Sketch is starting... ****\n"); 63 | 64 | // Setup IR-controller as receiver 65 | IR.begin(&ir_receiver); 66 | IR.scan(); 67 | 68 | 69 | 70 | } 71 | 72 | 73 | void loop() { 74 | 75 | 76 | // Check state of IR-controller 77 | ir_state = IR.getState(); 78 | 79 | if(!(ir_state & IR_STATUS_BUSY)) 80 | { 81 | // IR-Controller received a data 82 | digitalWrite(LED_PIN, HIGH); 83 | 84 | // Case 1 85 | // Control via RAW DATA 86 | 87 | if(IR.equals_raw16(raw_command_on)) 88 | { 89 | MY_SERIAL.println("\n GROUP1 ON\n"); 90 | zunoSendToGroupSetValueCommand(CONTROL_GROUP1, SWITCH_ON); 91 | } 92 | else 93 | if(IR.equals_raw16(raw_command_off)) 94 | { 95 | MY_SERIAL.println("\n GROUP1 OFF\n"); 96 | zunoSendToGroupSetValueCommand(CONTROL_GROUP1, SWITCH_OFF); 97 | } 98 | else 99 | // Case 2 100 | // Control via detected / known vedor specific command 101 | if(IR.detectCommand(&ir_cmd)) 102 | { 103 | if(ir_cmd.vendor == MY_IR_VENDOR) 104 | { 105 | 106 | if(ir_cmd.data[0] == MY_IR_VENDOR_CMD_ON) 107 | { 108 | MY_SERIAL.println("\n GROUP2 ON\n"); 109 | zunoSendToGroupSetValueCommand(CONTROL_GROUP2, SWITCH_ON); 110 | } 111 | else 112 | if(ir_cmd.data[0] == MY_IR_VENDOR_CMD_OFF) 113 | { 114 | MY_SERIAL.println("\n GROUP2 OFF\n"); 115 | zunoSendToGroupSetValueCommand(CONTROL_GROUP2, SWITCH_OFF); 116 | } 117 | 118 | 119 | } 120 | } 121 | // restart scan process 122 | IR.scan(); 123 | digitalWrite(LED_PIN, LOW); 124 | 125 | 126 | } 127 | delay(500); 128 | } 129 | 130 | 131 | 132 | 133 | -------------------------------------------------------------------------------- /hardware/examples/WaterMeter/WaterMeter.ino: -------------------------------------------------------------------------------- 1 | /* 2 | * This is a simple 2 chennel meter example 3 | * (c) Z-Wave.Me 2016 4 | */ 5 | 6 | #include 7 | 8 | // channel number 9 | #define ZUNO_CHANNEL_NUMBER_COLD 1 10 | #define ZUNO_CHANNEL_NUMBER_HOT 2 11 | 12 | #define PIN_COLD 0 13 | #define PIN_HOT 1 14 | 15 | #define PIN_PULSE 13 16 | 17 | #define EEPROM_ADDR 0x800 18 | #define EEPROM_UPDATE_INTERVAL 120000 19 | 20 | #define TICK_VALUE 10 // in liters 21 | 22 | 23 | struct meter_data 24 | { 25 | unsigned long ticks_cold; 26 | unsigned long ticks_hot; 27 | byte crc8; 28 | }; 29 | 30 | meter_data my_meter_data; 31 | 32 | unsigned long last_update_millis = 0; 33 | byte data_updated = FALSE; 34 | 35 | #define DEBOUNCE_COUNT 3 36 | byte cold_triggered = 0; 37 | byte cold_debounce = DEBOUNCE_COUNT; 38 | byte hot_triggered = 0; 39 | byte hot_debounce = DEBOUNCE_COUNT; 40 | 41 | 42 | 43 | // next macro sets up the Z-Uno channels 44 | // in this example we set up 1 meter channel 45 | // you can read more on http://z-uno.z-wave.me/Reference/ZUNO_SENSOR_MULTILEVEL/ 46 | ZUNO_SETUP_CHANNELS(ZUNO_METER(ZUNO_METER_TYPE_WATER, METER_RESET_ENABLE, ZUNO_METER_WATER_SCALE_METERS3, METER_SIZE_FOUR_BYTES, METER_PRECISION_THREE_DECIMALS, getterCold, resetterCold), 47 | ZUNO_METER(ZUNO_METER_TYPE_WATER, METER_RESET_ENABLE, ZUNO_METER_WATER_SCALE_METERS3, METER_SIZE_FOUR_BYTES, METER_PRECISION_THREE_DECIMALS, getterHot, resetterHot)); 48 | 49 | #define MY_SERIAL Serial0 50 | 51 | byte my_crc8(byte * data, byte count) 52 | { 53 | byte result = 0xDF; 54 | 55 | while(count--) 56 | { 57 | result ^= *data; 58 | data++; 59 | } 60 | return result; 61 | } 62 | void update_meter_data() 63 | { 64 | my_meter_data.crc8 = my_crc8((byte*)&my_meter_data, sizeof(meter_data) - 1); 65 | EEPROM.put(EEPROM_ADDR, &my_meter_data, sizeof(meter_data)); 66 | } 67 | void setup() { 68 | MY_SERIAL.begin(115200); 69 | MY_SERIAL.println("Starting Meter..."); 70 | 71 | // Dry contacts of meters connect to these pins 72 | pinMode(PIN_COLD, INPUT_PULLUP); 73 | pinMode(PIN_HOT, INPUT_PULLUP); 74 | 75 | // Get last meter values from EEPROM 76 | EEPROM.get(EEPROM_ADDR, &my_meter_data, sizeof(meter_data)); 77 | // Check data 78 | if(my_crc8((byte*)&my_meter_data, sizeof(meter_data) - 1) != my_meter_data.crc8) 79 | { 80 | // Invalid data - reset all 81 | MY_SERIAL.println("Bad eeprom crc8 - init meter data"); 82 | my_meter_data.ticks_cold = 0; 83 | my_meter_data.ticks_hot = 0; 84 | update_meter_data(); 85 | 86 | } 87 | 88 | } 89 | 90 | 91 | 92 | void loop() { 93 | 94 | 95 | if(!digitalRead(PIN_COLD)) 96 | { 97 | if(!cold_triggered) 98 | { 99 | cold_debounce--; 100 | if(!cold_debounce) 101 | { 102 | my_meter_data.ticks_cold++; 103 | data_updated = true; 104 | cold_triggered = true; 105 | MY_SERIAL.println("Cold++"); 106 | zunoSendReport(ZUNO_CHANNEL_NUMBER_COLD); 107 | } 108 | } 109 | } 110 | else 111 | { 112 | cold_debounce = DEBOUNCE_COUNT; 113 | cold_triggered = false; 114 | 115 | } 116 | if(!digitalRead(PIN_HOT)) 117 | { 118 | if(!hot_triggered) 119 | { 120 | hot_debounce--; 121 | if(!hot_debounce) 122 | { 123 | my_meter_data.ticks_hot++; 124 | data_updated = true; 125 | hot_triggered = true; 126 | MY_SERIAL.println("Hot++"); 127 | zunoSendReport(ZUNO_CHANNEL_NUMBER_HOT); 128 | } 129 | } 130 | 131 | } 132 | else 133 | { 134 | hot_debounce = DEBOUNCE_COUNT; 135 | hot_triggered = false; 136 | 137 | } 138 | // To save EEPROM from a lot of r/w operation 139 | // write it once in EEPROM_UPDATE_INTERVAL if data was updated 140 | if(data_updated && ( millis() - last_update_millis ) > EEPROM_UPDATE_INTERVAL ) 141 | { 142 | update_meter_data(); 143 | data_updated = false; 144 | last_update_millis = millis(); 145 | MY_SERIAL.println("Updating EEPROM"); 146 | } 147 | delay(100); 148 | 149 | } 150 | 151 | 152 | void resetterCold(byte v) { 153 | my_meter_data.ticks_cold = 0; 154 | update_meter_data(); 155 | MY_SERIAL.println("Cold meter was reset"); 156 | } 157 | void resetterHot(byte v) { 158 | my_meter_data.ticks_hot = 0; 159 | update_meter_data(); 160 | MY_SERIAL.println("Hot meter was reset"); 161 | } 162 | 163 | unsigned long getterCold(void) { 164 | return my_meter_data.ticks_cold*TICK_VALUE; 165 | } 166 | unsigned long getterHot(void) { 167 | return my_meter_data.ticks_hot*TICK_VALUE; 168 | } 169 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/string.h: -------------------------------------------------------------------------------- 1 | /*------------------------------------------------------------------------- 2 | string.h - ISO header for string library functions 3 | 4 | Copyright (C) 1998, Sandeep Dutta 5 | Copyright (C) 2009-2011, Philipp Klaus Krause pkk@spth.de 6 | 7 | This library is free software; you can redistribute it and/or modify it 8 | under the terms of the GNU General Public License as published by the 9 | Free Software Foundation; either version 2, or (at your option) any 10 | later version. 11 | 12 | This library is distributed in the hope that it will be useful, 13 | but WITHOUT ANY WARRANTY; without even the implied warranty of 14 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15 | GNU General Public License for more details. 16 | 17 | You should have received a copy of the GNU General Public License 18 | along with this library; see the file COPYING. If not, write to the 19 | Free Software Foundation, 51 Franklin Street, Fifth Floor, Boston, 20 | MA 02110-1301, USA. 21 | 22 | As a special exception, if you link this library with other files, 23 | some of which are compiled with SDCC, to produce an executable, 24 | this library does not by itself cause the resulting executable to 25 | be covered by the GNU General Public License. This exception does 26 | not however invalidate any other reasons why the executable file 27 | might be covered by the GNU General Public License. 28 | -------------------------------------------------------------------------*/ 29 | 30 | #ifndef __SDCC_STRING_H 31 | #define __SDCC_STRING_H 1 32 | 33 | #ifndef NULL 34 | # define NULL (void *)0 35 | #endif 36 | 37 | #ifndef __SIZE_T_DEFINED 38 | # define __SIZE_T_DEFINED 39 | typedef unsigned int size_t; 40 | #endif 41 | 42 | /* Bounds-checking interfaces from annex K of the C11 standard. */ 43 | #if defined (__STDC_WANT_LIB_EXT1__) && __STDC_WANT_LIB_EXT1__ 44 | 45 | #ifndef __RSIZE_T_DEFINED 46 | #define __RSIZE_T_DEFINED 47 | typedef size_t rsize_t; 48 | #endif 49 | 50 | #ifndef __ERRNO_T_DEFINED 51 | #define __ERRNO_T_DEFINED 52 | typedef int errno_t; 53 | #endif 54 | 55 | #endif 56 | 57 | #if defined(__SDCC_mcs51) || defined(__SDCC_hc08) || defined(__SDCC_ds390) || defined(__SDCC_pic14) || defined(__SDCC_pic16) 58 | #define __SDCC_BROKEN_STRING_FUNCTIONS 59 | #endif 60 | 61 | /* The function prototypes are ordered as in the ISO C99 standard. */ 62 | 63 | /* Todo: fix the "restrict" stuff for C99 compliance. */ 64 | 65 | /* Copying functions: */ 66 | extern void *memcpy (void * /*restrict */ dest, const void * /*restrict*/ src, size_t n); 67 | extern void *memmove (void *dest, const void *src, size_t n); 68 | extern char *strcpy (char * /*restrict*/ dest, const char * /*restrict*/ src); 69 | extern char *strncpy(char * /*restrict*/ dest, const char * /*restrict*/ src, size_t n); 70 | 71 | /* Concatenation functions: */ 72 | extern char *strcat (char * /*restrict*/ dest, const char * /*restrict*/ src); 73 | extern char *strncat(char * /*restrict*/ dest, const char * /*restrict*/ src, size_t n); 74 | 75 | /* Comparison functions: */ 76 | extern int memcmp (const void *s1, const void *s2, size_t n); 77 | extern int strcmp (const char *s1, const char *s2); 78 | #define strcoll(s1, s2) strcmp(s1, s2) 79 | /*int strcoll(const char *s1, const char *s2) {return strcmp(s1, s2);}*/ 80 | extern int strncmp(const char *s1, const char *s2, size_t n); 81 | extern size_t strxfrm(char *dest, const char *src, size_t n); 82 | 83 | /* Search functions: */ 84 | extern void *memchr (const void *s, int c, size_t n); 85 | #ifdef __SDCC_BROKEN_STRING_FUNCTIONS 86 | extern char *strchr (const char *s, char c); /* c should be int according to standard. */ 87 | #else 88 | extern char *strchr (const char *s, int c); 89 | #endif 90 | extern size_t strcspn(const char *s, const char *reject); 91 | extern char *strpbrk(const char *s, const char *accept); 92 | #ifdef __SDCC_BROKEN_STRING_FUNCTIONS 93 | extern char *strrchr(const char *s, char c); /* c should be int according to standard. */ 94 | #else 95 | extern char *strrchr(const char *s, int c); 96 | #endif 97 | extern size_t strspn (const char *s, const char *accept); 98 | extern char *strstr (const char *haystack, const char *needle); 99 | extern char *strtok (char * /* restrict*/ str, const char * /*restrict*/ delim); 100 | 101 | /* Miscanelleous functions: */ 102 | #ifdef __SDCC_BROKEN_STRING_FUNCTIONS 103 | extern void *memset (void *s, unsigned char c, size_t n); /* c should be int according to standard. */ 104 | #else 105 | extern void *memset (void *s, int c, size_t n); 106 | #endif 107 | 108 | /* extern char *strerror(int errnum); */ 109 | extern size_t strlen (const char *s); 110 | 111 | #ifdef __SDCC_ds390 112 | extern void __xdata * memcpyx(void __xdata *, void __xdata *, int) __naked; 113 | #endif 114 | 115 | #if defined(__SDCC_z80) || defined(__SDCC_z180) || defined(__SDCC_r2k) || defined(__SDCC_r3ka) 116 | #define memcpy(dst, src, n) __builtin_memcpy(dst, src, n) 117 | #define strcpy(dst, src) __builtin_strcpy(dst, src) 118 | #define strncpy(dst, src, n) __builtin_strncpy(dst, src, n) 119 | #define strchr(s, c) __builtin_strchr(s, c) 120 | #define memset(dst, c, n) __builtin_memset(dst, c, n) 121 | #endif 122 | 123 | #endif 124 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/Stream.h: -------------------------------------------------------------------------------- 1 | /* 2 | Stream.h - base class for character-based streams. 3 | Copyright (c) 2010 David A. Mellis. All right reserved. 4 | 5 | This library is free software; you can redistribute it and/or 6 | modify it under the terms of the GNU Lesser General Public 7 | License as published by the Free Software Foundation; either 8 | version 2.1 of the License, or (at your option) any later version. 9 | 10 | This library is distributed in the hope that it will be useful, 11 | but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 13 | Lesser General Public License for more details. 14 | 15 | You should have received a copy of the GNU Lesser General Public 16 | License along with this library; if not, write to the Free Software 17 | Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 18 | 19 | parsing functions based on TextFinder library by Michael Margolis 20 | */ 21 | 22 | #ifndef Stream_h 23 | #define Stream_h 24 | 25 | #include "Print.h" 26 | 27 | struct MultiTarget { 28 | char *str; // string you're searching for 29 | size_t len; // length of string you're searching for 30 | size_t index; // index used by the search routine. 31 | }; 32 | 33 | 34 | // compatability macros for testing 35 | /* 36 | #define getInt() parseInt() 37 | #define getInt(skipChar) parseInt(skipchar) 38 | #define getFloat() parseFloat() 39 | #define getFloat(skipChar) parseFloat(skipChar) 40 | #define getString( pre_string, post_string, buffer, length) 41 | readBytesBetween( pre_string, terminator, buffer, length) 42 | */ 43 | 44 | class Stream : public Print 45 | { 46 | protected: 47 | unsigned long _timeout; // number of milliseconds to wait for the next char before aborting timed read 48 | unsigned long _startMillis; // used for timeout measurement 49 | int timedRead(); // private method to read stream with timeout 50 | int timedPeek(); // private method to peek stream with timeout 51 | int peekNextDigit(); // returns the next numeric digit in the stream or -1 if timeout 52 | 53 | public: 54 | virtual int available(){return 0;}; //= 0; 55 | virtual int read(){return 0;}; //= 0; 56 | virtual int peek(){return 0;};// = 0; 57 | virtual void flush(){};// = 0; 58 | 59 | Stream() {_timeout=1000;} 60 | 61 | // parsing methods 62 | 63 | void setTimeout(unsigned long timeout); // sets maximum milliseconds to wait for stream data, default is 1 second 64 | 65 | bool find(char *target); // reads data from the stream until the target string is found 66 | bool find(uint8_t *target) { return find ((char *)target); } 67 | // returns true if target string is found, false if timed out (see setTimeout) 68 | 69 | bool find(char *target, size_t length); // reads data from the stream until the target string of given length is found 70 | bool find(uint8_t *target, size_t length) { return find ((char *)target, length); } 71 | // returns true if target string is found, false if timed out 72 | 73 | bool find(char target) { return find (&target, 1); } 74 | 75 | bool findUntil(char *target, char *terminator); // as find but search ends if the terminator string is found 76 | bool findUntil(uint8_t *target, char *terminator) { return findUntil((char *)target, terminator); } 77 | 78 | bool findUntil(char *target, size_t targetLen, char *terminate, size_t termLen); // as above but search ends if the terminate string is found 79 | //bool findUntil(uint8_t *target, size_t targetLen, char *terminate, size_t termLen) {return findUntil((char *)target, targetLen, terminate, termLen); } 80 | 81 | 82 | long parseInt(); // returns the first valid (long) integer value from the current position. 83 | // initial characters that are not digits (or the minus sign) are skipped 84 | // integer is terminated by the first character that is not a digit. 85 | 86 | float parseFloat(); // float version of parseInt 87 | 88 | size_t readBytes( char *buffer, size_t length); // read chars from stream into buffer 89 | size_t readBytes( uint8_t *buffer, size_t length) { return readBytes((char *)buffer, length); } 90 | // terminates if length characters have been read or timeout (see setTimeout) 91 | // returns the number of characters placed in the buffer (0 means no valid data found) 92 | 93 | size_t readBytesUntil( char terminator, char *buffer, size_t length); // as readBytes with terminator character 94 | size_t readBytesUntil( char terminator, uint8_t *buffer, size_t length) { return readBytesUntil(terminator, (char *)buffer, length); } 95 | // terminates if length characters have been read, timeout, or if the terminator character detected 96 | // returns the number of characters placed in the buffer (0 means no valid data found) 97 | 98 | 99 | protected: 100 | long parseInt(char skipChar); // as above but the given skipChar is ignored 101 | // as above but the given skipChar is ignored 102 | // this allows format characters (typically commas) in values to be ignored 103 | 104 | float parseFloat(char skipChar); // as above but the given skipChar is ignored 105 | 106 | // This allows you to search for an arbitrary number of strings. 107 | // Returns index of the target that is found first or -1 if timeout occurs. 108 | int findMulti(struct MultiTarget *targets, int tCount); 109 | }; 110 | 111 | 112 | #endif 113 | -------------------------------------------------------------------------------- /hardware/examples/ZWave2IR/ZWave2IR.ino: -------------------------------------------------------------------------------- 1 | /* 2 | * Receives ON/OFF command via Z-Wave and 3 | * sends specified IR command using built-in IR-controller of Z-Uno 4 | * 5 | * (c) Z-Wave.Me 2016 6 | */ 7 | 8 | #include 9 | 10 | // You have to connect your IR-LED to PIN#6 of Z-Uno 11 | // In other hand you can use PIN#4/PIN#5 for that purpose too - just modify the next string 12 | IRTransmitterParams ir_transmitter(byte(IR_TRANSMITTER_OUTPUT_PIN6), 13 | IR_FLAGS_OUTPUT_HIGHDRIVE, 14 | IR_MS_PRESCALLER_4MHZ, 15 | IR_CARRIER_PRESCALLER_8MHZ); 16 | 17 | // LED pin number 18 | #define LED_PIN 13 19 | 20 | #define MY_SERIAL Serial0 21 | #define SWITCH_ON 0xff 22 | #define SWITCH_OFF 0 23 | 24 | 25 | // Use IRScanner.ino as IR-sniffer 26 | // Sniffed raw16 commands 27 | // This codes were shiffed from SONY TV IRController 28 | // RAW: ON/OFF Decoded: MUTE/MUTE 29 | word raw_command_on[] = {0x19, 0x990, 0x242, 0x26D, 0x243, 0x26C, 0x244, 0x26A, 0x246, 0x4C5, 0x243, 0x4BD, 0x24B, 0x4C0, 0x248, 0x267, 0x249, 0x4C2, 0x246, 0x269, 0x247, 0x267, 0x249, 0x265, 0x24B, 0x264}; 30 | word raw_command_off[] = {0x19, 0x987, 0x24B, 0x4C0, 0x248, 0x267, 0x249, 0x4C2, 0x247, 0x268, 0x248, 0x4C3, 0x245, 0x269, 0x246, 0x268, 0x248, 0x4C3, 0x245, 0x26A, 0x246, 0x269, 0x247, 0x267, 0x249, 0x266}; 31 | 32 | // Detected vendor 33 | 34 | #define MY_IR_VENDOR IR_VENDOR_SONY // Use SONY protocol. See IRController.h for more details. 35 | // Decoded commands 36 | #define MY_IR_VENDOR_CMD_ON 0x290 37 | #define MY_IR_VENDOR_CMD_OFF 0x290 38 | #define DECODED_COMMAND_NBITS 12 39 | 40 | // Last saved LED value 41 | byte currentCh1 = 0; 42 | byte currentCh2 = 0; 43 | byte current_cmd = 0; 44 | IRCommand_t vendor_cmd; 45 | 46 | ZUNO_SETUP_DEBUG_MODE(DEBUG_ON); 47 | 48 | // next macro sets up the Z-Uno channels 49 | // in this example we set up 2 switch binary channels 50 | // you can read more on http://z-uno.z-wave.me/Reference/ZUNO_SWITCH_BINARY/ 51 | ZUNO_SETUP_CHANNELS(ZUNO_SWITCH_BINARY(getter1, setter1), 52 | ZUNO_SWITCH_BINARY(getter2, setter2)); 53 | 54 | 55 | void setup() { 56 | pinMode(LED_PIN, OUTPUT); // setup pin as output 57 | // We have to setup IRLED pin as output 58 | pinMode(6, OUTPUT); 59 | digitalWrite(6, LOW); 60 | 61 | MY_SERIAL.begin(115200); 62 | MY_SERIAL.println("\n **** Sketch is starting... ****\n"); 63 | 64 | // setting up IR-controller as IR-transmitter 65 | ir_transmitter.setupVendor(MY_IR_VENDOR); 66 | IR.begin(&ir_transmitter); 67 | 68 | vendor_cmd.vendor = MY_IR_VENDOR; 69 | vendor_cmd.n_bits = DECODED_COMMAND_NBITS; 70 | 71 | } 72 | void sendRAWCommand(WORD * raw16) 73 | { 74 | // we have to repeat packet 75 | // like another IR-controllers do 76 | byte count = 7; 77 | while(count--) 78 | { 79 | IR.send_raw16(raw16); 80 | delay(30); 81 | } 82 | } 83 | void sendVendorCommand(unsigned long cmd) 84 | { 85 | // we have to repeat packet 86 | // like another IR-controllers do 87 | byte count = 7; 88 | while(count--) 89 | { 90 | vendor_cmd.data[0] = cmd; 91 | IR.sendCommand(&vendor_cmd); 92 | delay(30); 93 | } 94 | } 95 | void loop() { 96 | 97 | switch(current_cmd) 98 | { 99 | case 1: 100 | MY_SERIAL.println("\n RAW ON\n"); 101 | sendRAWCommand(raw_command_on); 102 | break; 103 | case 2: 104 | MY_SERIAL.println("\n RAW OFF\n"); 105 | sendRAWCommand(raw_command_off); 106 | break; 107 | case 3: 108 | MY_SERIAL.println("\n VENDOR ON\n"); 109 | sendVendorCommand(MY_IR_VENDOR_CMD_ON); 110 | break; 111 | case 4: 112 | MY_SERIAL.println("\n VENDOR OFF\n"); 113 | sendVendorCommand(MY_IR_VENDOR_CMD_OFF); 114 | break; 115 | 116 | default: 117 | // nothing to do 118 | break; 119 | 120 | } 121 | 122 | current_cmd = 0; 123 | 124 | delay(500); 125 | } 126 | 127 | // function, which sets new channel state 128 | // this function runs only once the controller sends new value 129 | void setter1 (byte value) { 130 | // value is a variable, holding a "new value" 131 | // which came from the controller or other Z-Wave device 132 | if (value > 0) { // if greater then zero 133 | current_cmd = 1; // will be dispatched in the next loop 134 | 135 | } else { // if equals zero 136 | current_cmd = 2; 137 | } 138 | // let's save our value for the situation, when the controller will ask us about it 139 | currentCh1 = value; 140 | } 141 | 142 | // function, which returns the previously saved relay value 143 | // this function runs only once the controller asks 144 | byte getter1 (){ 145 | return currentCh1; 146 | } 147 | 148 | // function, which sets new relay state 149 | // this function runs only once the controller sends new value 150 | void setter2 (byte value) { 151 | // value is a variable, holding a "new value" 152 | // which came from the controller or other Z-Wave device 153 | if (value > 0) { // if greater then zero 154 | current_cmd = 3; // will be dispatched in the next loop 155 | 156 | } else { // if equals zero 157 | current_cmd = 4; 158 | } 159 | // let's save our value for the situation, when the controller will ask us about it 160 | currentCh2 = value; 161 | } 162 | 163 | // function, which returns the previously saved relay value 164 | // this function runs only once the controller asks 165 | byte getter2 (){ 166 | return currentCh2; 167 | } -------------------------------------------------------------------------------- /hardware/examples/Certified10Channels/Certified10Channels.ino: -------------------------------------------------------------------------------- 1 | /* 2 | * This scretch was certified by the Z-Wave Alliance as one of the two reference Z-Uno sketches. 3 | * 4 | * 3 switches 5 | * 3 dimmers 6 | * 1 motion sensor 7 | * 1 temperature sensor 8 | * 1 luminance sensor 9 | * 1 door sensor 10 | * 11 | */ 12 | 13 | // Pins definitions 14 | #define LedPin1 9 15 | #define LedPin2 10 16 | #define LedPin3 11 17 | #define LedPin4 PWM2 18 | #define LedPin5 PWM3 19 | #define LedPin6 PWM4 20 | #define MotionPin 12 21 | #define LumiPin A2 22 | #define TemperaturePin A3 23 | #define DoorPin 19 24 | 25 | #define SWITCH_ON 0xff 26 | #define SWITCH_OFF 0 27 | 28 | // Global variables to store data reported via getters 29 | byte switchValue1 = 0; 30 | byte switchValue2 = 0; 31 | byte switchValue3 = 0; 32 | byte dimValue1 = 0; 33 | byte dimValue2 = 0; 34 | byte dimValue3 = 0; 35 | byte lastMotionValue = 0; 36 | byte lastLumiValue = 0; 37 | byte lastTemperatureValue = 0; 38 | byte lastDoorValue = 0; 39 | word relaxMotion = 0; 40 | 41 | ZUNO_SETUP_SLEEPING_MODE(ZUNO_SLEEPING_MODE_ALWAYS_AWAKE); 42 | 43 | ZUNO_SETUP_ASSOCIATIONS(ZUNO_ASSOCIATION_GROUP_SET_VALUE); // Send Basic Set to association group 44 | 45 | // Set up 10 channels 46 | ZUNO_SETUP_CHANNELS( 47 | ZUNO_SWITCH_BINARY(getterSwitch1, setterSwitch1), 48 | ZUNO_SWITCH_BINARY(getterSwitch2, setterSwitch2), 49 | ZUNO_SWITCH_BINARY(getterSwitch3, setterSwitch3), 50 | ZUNO_SWITCH_MULTILEVEL(getterDim1, setterDim1), 51 | ZUNO_SWITCH_MULTILEVEL(getterDim2, setterDim2), 52 | ZUNO_SWITCH_MULTILEVEL(getterDim3, setterDim3), 53 | ZUNO_SENSOR_BINARY_MOTION(getterMotion), 54 | ZUNO_SENSOR_MULTILEVEL(ZUNO_SENSOR_MULTILEVEL_TYPE_LUMINANCE, SENSOR_MULTILEVEL_SCALE_PERCENTAGE_VALUE, SENSOR_MULTILEVEL_SIZE_ONE_BYTE, SENSOR_MULTILEVEL_PRECISION_ZERO_DECIMALS, getterLuminance), 55 | ZUNO_SENSOR_MULTILEVEL_TEMPERATURE(getterTemperature), 56 | ZUNO_SENSOR_BINARY_DOOR_WINDOW(getterDoor) 57 | ); 58 | 59 | void setup() { 60 | // set up I/O pins. Analog and PWM will be automatically set up on analogRead/analogWrite functions call 61 | pinMode(LedPin1, OUTPUT); 62 | pinMode(LedPin2, OUTPUT); 63 | pinMode(LedPin3, OUTPUT); 64 | pinMode(MotionPin, INPUT_PULLUP); 65 | pinMode(DoorPin, INPUT_PULLUP); 66 | } 67 | 68 | void loop() { 69 | byte currentMotionValue; 70 | byte currentLumiValue; 71 | byte currentTemperatureValue; 72 | byte currentDoorValue; 73 | 74 | // Trigger motion and wait for relax (about 5 sec) before report idle 75 | currentMotionValue = !digitalRead(MotionPin); 76 | if (currentMotionValue) { 77 | if (relaxMotion == 0) { 78 | lastMotionValue = 1; 79 | zunoSendReport(7); 80 | zunoSendToGroupSetValueCommand(CTRL_GROUP_1, SWITCH_ON); 81 | } 82 | relaxMotion = 1900; // impirical for ~5 sec relax time 83 | } 84 | if (lastMotionValue == 1 && relaxMotion == 0) { 85 | lastMotionValue = 0; 86 | zunoSendReport(7); 87 | zunoSendToGroupSetValueCommand(CTRL_GROUP_1, SWITCH_OFF); 88 | } 89 | if (relaxMotion) relaxMotion--; 90 | 91 | // Luminosity 92 | currentLumiValue = (byte)(100 - analogRead(LumiPin)*25/256); 93 | if ((currentLumiValue > (lastLumiValue + 5)) || (currentLumiValue < (lastLumiValue - 5))) { 94 | lastLumiValue = currentLumiValue; 95 | zunoSendReport(8); 96 | } 97 | 98 | // TMP36 analog temperature sensor 99 | currentTemperatureValue = analogRead(TemperaturePin) * 40 / 124 - 50; // from TMP36 spec (40/124 ~= 3.3*100/1024) 100 | if ((currentTemperatureValue > (lastTemperatureValue + 1)) || (currentTemperatureValue < (lastTemperatureValue - 1))) { 101 | lastTemperatureValue = currentTemperatureValue; 102 | zunoSendReport(9); 103 | } 104 | 105 | // Door/Window sensor 106 | currentDoorValue = digitalRead(DoorPin); 107 | if (currentDoorValue != lastDoorValue) { 108 | lastDoorValue = currentDoorValue; 109 | zunoSendReport(10); 110 | } 111 | } 112 | 113 | // Getters and setters 114 | 115 | void setterSwitch1(byte value) { 116 | digitalWrite(LedPin1, (value > 0) ? HIGH : LOW); 117 | switchValue1 = value; 118 | } 119 | 120 | byte getterSwitch1(){ 121 | return switchValue1; 122 | } 123 | 124 | void setterSwitch2(byte value) { 125 | digitalWrite(LedPin2, (value > 0) ? HIGH : LOW); 126 | switchValue2 = value; 127 | } 128 | 129 | byte getterSwitch2(){ 130 | return switchValue2; 131 | } 132 | 133 | void setterSwitch3(byte value) { 134 | digitalWrite(LedPin3, (value > 0) ? HIGH : LOW); 135 | switchValue3 = value; 136 | } 137 | 138 | byte getterSwitch3(){ 139 | return switchValue3; 140 | } 141 | 142 | void setterDim1(byte value) { 143 | if (value > 99) value = 99; 144 | analogWrite(LedPin4, ((word)value)*255/99); 145 | dimValue1 = value; 146 | } 147 | 148 | byte getterDim1(void) { 149 | return dimValue1; 150 | } 151 | 152 | void setterDim2(byte value) { 153 | if (value > 99) value = 99; 154 | analogWrite(LedPin5, ((word)value)*255/99); 155 | dimValue2 = value; 156 | } 157 | 158 | byte getterDim2(void) { 159 | return dimValue2; 160 | } 161 | 162 | void setterDim3(byte value) { 163 | if (value > 99) value = 99; 164 | analogWrite(LedPin6, ((word)value)*255/99); 165 | dimValue3 = value; 166 | } 167 | 168 | byte getterDim3(void) { 169 | return dimValue3; 170 | } 171 | 172 | byte getterMotion(void) { 173 | return lastMotionValue ? 0xff : 0; 174 | } 175 | 176 | byte getterLuminance(void) { 177 | return lastLumiValue; 178 | } 179 | 180 | byte getterTemperature(void) { 181 | return lastTemperatureValue; 182 | } 183 | 184 | byte getterDoor(void) { 185 | return lastDoorValue ? 0xff : 0; 186 | } 187 | 188 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_DHTlib/ZUNO_DHT.cpp: -------------------------------------------------------------------------------- 1 | /* DHT library 2 | 3 | MIT license 4 | written by Adafruit Industries 5 | 6 | UPGRADED/Rewriten by Z-Wave>ME for project Z-Uno 2016 7 | */ 8 | 9 | #include "ZUNO_DHT.h" 10 | 11 | #define MIN_INTERVAL 2000 12 | 13 | #define DEBUG_DHT 0 14 | 15 | DHT::DHT(uint8_t pin, uint8_t type): _pin(pin) 16 | { 17 | _type = type; 18 | // reading pulses from DHT sensor. 19 | 20 | } 21 | 22 | void DHT::begin(void) { 23 | // set up the pins! 24 | pinMode(_pin, INPUT_PULLUP); 25 | _lastreadtime = 0; 26 | } 27 | 28 | // returns temperature in 10 th of Celsius 29 | int DHT::readTemperatureC10(bool force) 30 | { 31 | 32 | if(read(force) > DHT_RESULT_PREVIOUS) 33 | return BAD_DHT_VALUE; 34 | 35 | return temperature; 36 | 37 | } 38 | // returns humidity in 10 th of percent 39 | int DHT::readHumidityH10(bool force) 40 | { 41 | if(read(force) > DHT_RESULT_PREVIOUS) 42 | return BAD_DHT_VALUE; 43 | return humidity; 44 | } 45 | 46 | // Returns temperature in float in Celsius 47 | float DHT::readTemperature(bool force) 48 | { 49 | return readTemperatureC10(force) / 10.0; 50 | } 51 | // Returns humidity in float 52 | float DHT::readHumidity(bool force) 53 | { 54 | return readHumidityH10(force) / 10.0; 55 | } 56 | 57 | 58 | 59 | // DBG 60 | #if DEBUG_DHT 61 | byte dbg_timings_s[80]; 62 | #endif 63 | 64 | 65 | byte DHT::read(bool force) { 66 | 67 | byte time_i1, time_i2; 68 | word wi = 0; 69 | byte time_ref; 70 | //s_pin tp = 12; 71 | byte i = 0; 72 | byte ci = 0; 73 | byte cb =0; 74 | 75 | 76 | 77 | //pinMode(tp, OUTPUT); 78 | //digitalWrite(tp, 0); 79 | 80 | // Чтобы не опрашивать сенсор слишком часто 81 | uint32_t currenttime = millis(); 82 | if (!force && ((currenttime - _lastreadtime) < 2000)) { 83 | return DHT_RESULT_PREVIOUS; // return last correct measurement 84 | } 85 | _lastreadtime = currenttime; 86 | 87 | 88 | // Посылаем стартовый импульс 89 | // 0 на 1 мс и болльше 90 | //noInterrupts(); 91 | pinMode(_pin, OUTPUT); 92 | digitalWrite(_pin, LOW); // Send start signal 93 | switch(_type) 94 | { 95 | case DHT11: 96 | delay(13); // Датчик долго думает 97 | break; 98 | default: 99 | delayMicroseconds(1400); // Гораздо быстрее откликается 100 | break; 101 | } 102 | pinMode(_pin, INPUT_PULLUP); 103 | 104 | noInterrupts(); 105 | time_i1 = 0; 106 | while(digitalRead(_pin))//digitalRead(_pin)) 107 | { 108 | wi++; 109 | if(!wi) 110 | { 111 | interrupts(); 112 | return DHT_RESULT_ERROR_NOSYNC; 113 | } 114 | NOPS(8); 115 | } 116 | time_i1 = 0; 117 | while(!digitalRead(_pin)) 118 | { 119 | time_i1++; 120 | if(!time_i1) 121 | break; 122 | } 123 | time_i2 = 0; 124 | while(digitalRead(_pin)) 125 | { 126 | time_i2++; 127 | if(!time_i2) 128 | break; 129 | } 130 | 131 | if(time_i1 < 10 || time_i2 < 10) 132 | { 133 | 134 | interrupts(); 135 | return DHT_RESULT_ERROR_NOSYNC; 136 | } 137 | 138 | // Вычисляем опорное время для "1" 139 | // == Половина среднего времени отклика датчика 140 | // Вычисляется здесь т.к. 141 | // время стартового интервала будет плавать в цикле чтения битов 142 | // особенно это заметно на каждом 8-ом бите 143 | time_ref = time_i1 + time_i2; 144 | time_ref >>= 2; 145 | 146 | while(i<80) 147 | { 148 | 149 | switch(i&0x01) 150 | { 151 | case 0: 152 | time_i1 = 0; 153 | while(!digitalRead(_pin)) time_i1++; 154 | #if DEBUG_DHT 155 | dbg_timings_s[i] = time_i1; 156 | #endif 157 | break; 158 | case 1: 159 | time_i2 = 0; 160 | while(digitalRead(_pin)) time_i2++; 161 | #if DEBUG_DHT 162 | dbg_timings_s[i] = time_i2; 163 | #endif 164 | cb <<= 1; 165 | cb |= (time_i2 > time_ref); 166 | break; 167 | } 168 | 169 | i++; 170 | if((i & 0x0F)==0) 171 | { 172 | data_ptr[ci++] = cb; 173 | cb = 0; 174 | } 175 | } 176 | 177 | interrupts(); 178 | 179 | 180 | 181 | #if DEBUG_DHT 182 | Serial.print("TIMINGS \n"); 183 | for(i=0;i<80;i++) 184 | { 185 | Serial.print("EDGE #"); 186 | Serial.print(i); 187 | Serial.print(" "); 188 | Serial.println(dbg_timings_s[i]); 189 | 190 | } 191 | Serial.print("RAW "); 192 | for(i=0;i<5;i++) 193 | { 194 | Serial.print((uint16_t)data_ptr[i], HEX); 195 | Serial.print(" "); 196 | } 197 | Serial.println(" "); 198 | #endif 199 | 200 | byte sum = data_ptr[0]; 201 | sum += data_ptr[1]; 202 | sum += data_ptr[2]; 203 | sum += data_ptr[3]; 204 | 205 | 206 | if ( sum != data_ptr[4]) 207 | { 208 | #if DEBUG_DHT 209 | Serial.print(" Calculated sum: "); 210 | Serial.print(sum, HEX); 211 | Serial.println(" "); 212 | #endif 213 | return DHT_RESULT_ERROR_CRC; 214 | } 215 | 216 | 217 | 218 | 219 | if(_type == DHT11) 220 | { 221 | humidity = data_ptr[0]; 222 | temperature = data_ptr[2]; 223 | humidity *= 10; 224 | temperature *= 10; 225 | } 226 | else 227 | { 228 | 229 | humidity = data_ptr[0]; 230 | humidity <<= 8; 231 | humidity += data_ptr[1]; 232 | 233 | temperature = data_ptr[2] & ~(0x80); 234 | temperature <<= 8; 235 | temperature += data_ptr[3]; 236 | if ( data_ptr[2] & 0x80) 237 | temperature -= temperature; 238 | 239 | 240 | } 241 | 242 | return DHT_RESULT_OK; 243 | } 244 | 245 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_DallasRTC/ZUNO_DS3232RTC.h: -------------------------------------------------------------------------------- 1 | /*----------------------------------------------------------------------* 2 | * DS3232RTC.h - Arduino library for the Maxim Integrated DS3232 * 3 | * Real-Time Clock. This library is intended for use with the Arduino * 4 | * Time.h library, http://www.arduino.cc/playground/Code/Time * 5 | * * 6 | * This library is a drop-in replacement for the DS1307RTC.h library * 7 | * by Michael Margolis that is supplied with the Arduino Time library * 8 | * above. To change from using a DS1307 RTC to an DS3232 RTC, it is * 9 | * only necessary to change the #include statement to include this * 10 | * library instead of DS1307RTC.h. * 11 | * * 12 | * This library is *not* a drop-in replacement for the newer version * 13 | * of the DS1307RTC library at * 14 | * http://www.pjrc.com/teensy/td_libs_DS1307RTC.html * 15 | * * 16 | * In addition, this library implements functions to support the * 17 | * additional features of the DS3232. * 18 | * * 19 | * This library will also work with the DS3231 RTC, which has the same * 20 | * features of the DS3232 except: (1) Battery-backed SRAM, (2) Battery- * 21 | * backed 32kHz output (BB32kHz bit in Control/Status register 0x0F), * 22 | * and (3) Adjustable temperature sensor sample rate (CRATE1:0 bits in * 23 | * the Control/Status register). * 24 | * * 25 | * Whether used with the DS3232 or DS3231, the user is responsible for * 26 | * ensuring reads and writes do not exceed the device's address space * 27 | * (0x00-0x12 for DS3231, 0x00-0xFF for DS3232); no bounds checking * 28 | * is done by this library. * 29 | * * 30 | * Jack Christensen 06Mar2013 * 31 | * http://github.com/JChristensen/DS3232RTC * 32 | * * 33 | * CC BY-SA 4.0 * 34 | * "Arduino DS3232RTC Library" by Jack Christensen is licensed under * 35 | * CC BY-SA 4.0, http://creativecommons.org/licenses/by-sa/4.0/ * 36 | *----------------------------------------------------------------------*/ 37 | 38 | #ifndef DS3232RTC_h 39 | #define DS3232RTC_h 40 | 41 | 42 | 43 | 44 | 45 | #include 46 | 47 | #define tmYearToY2k(Y) ((Y) - 30) // offset is from 2000 48 | #define y2kYearToTm(Y) ((Y) + 30) 49 | 50 | //DS3232 I2C Address 51 | #define RTC_ADDR 0x68 52 | 53 | //DS3232 Register Addresses 54 | #define RTC_SECONDS 0x00 55 | #define RTC_MINUTES 0x01 56 | #define RTC_HOURS 0x02 57 | #define RTC_DAY 0x03 58 | #define RTC_DATE 0x04 59 | #define RTC_MONTH 0x05 60 | #define RTC_YEAR 0x06 61 | #define ALM1_SECONDS 0x07 62 | #define ALM1_MINUTES 0x08 63 | #define ALM1_HOURS 0x09 64 | #define ALM1_DAYDATE 0x0A 65 | #define ALM2_MINUTES 0x0B 66 | #define ALM2_HOURS 0x0C 67 | #define ALM2_DAYDATE 0x0D 68 | #define RTC_CONTROL 0x0E 69 | #define RTC_STATUS 0x0F 70 | #define RTC_AGING 0x10 71 | #define TEMP_MSB 0x11 72 | #define TEMP_LSB 0x12 73 | #define SRAM_START_ADDR 0x14 //first SRAM address 74 | #define SRAM_SIZE 236 //number of bytes of SRAM 75 | 76 | //Alarm mask bits 77 | #define A1M1 7 78 | #define A1M2 7 79 | #define A1M3 7 80 | #define A1M4 7 81 | #define A2M2 7 82 | #define A2M3 7 83 | #define A2M4 7 84 | 85 | //Control register bits 86 | #define EOSC 7 87 | #define BBSQW 6 88 | #define CONV 5 89 | #define RS2 4 90 | #define RS1 3 91 | #define INTCN 2 92 | #define A2IE 1 93 | #define A1IE 0 94 | 95 | //Status register bits 96 | #define OSF 7 97 | #define BB32KHZ 6 98 | #define CRATE1 5 99 | #define CRATE0 4 100 | #define EN32KHZ 3 101 | #define BSY 2 102 | #define A2F 1 103 | #define A1F 0 104 | 105 | //Square-wave output frequency (TS2, RS1 bits) 106 | enum SQWAVE_FREQS_t {SQWAVE_1_HZ, SQWAVE_1024_HZ, SQWAVE_4096_HZ, SQWAVE_8192_HZ, SQWAVE_NONE}; 107 | 108 | //Alarm masks 109 | enum ALARM_TYPES_t { 110 | ALM1_EVERY_SECOND = 0x0F, 111 | ALM1_MATCH_SECONDS = 0x0E, 112 | ALM1_MATCH_MINUTES = 0x0C, //match minutes *and* seconds 113 | ALM1_MATCH_HOURS = 0x08, //match hours *and* minutes, seconds 114 | ALM1_MATCH_DATE = 0x00, //match date *and* hours, minutes, seconds 115 | ALM1_MATCH_DAY = 0x10, //match day *and* hours, minutes, seconds 116 | ALM2_EVERY_MINUTE = 0x8E, 117 | ALM2_MATCH_MINUTES = 0x8C, //match minutes 118 | ALM2_MATCH_HOURS = 0x88, //match hours *and* minutes 119 | ALM2_MATCH_DATE = 0x80, //match date *and* hours, minutes 120 | ALM2_MATCH_DAY = 0x90, //match day *and* hours, minutes 121 | }; 122 | 123 | #define ALARM_1 1 //constants for calling functions 124 | #define ALARM_2 2 125 | 126 | //Other 127 | #define DS1307_CH 7 //for DS1307 compatibility, Clock Halt bit in Seconds register 128 | #define HR1224 6 //Hours register 12 or 24 hour mode (24 hour mode==0) 129 | #define CENTURY 7 //Century bit in Month register 130 | #define DYDT 6 //Day/Date flag bit in alarm Day/Date registers 131 | 132 | class DS3232RTC 133 | { 134 | public: 135 | DS3232RTC(); 136 | /*static time_t get(void); //must be static to work with setSyncProvider() in the Time library 137 | byte set(time_t t);*/ 138 | byte read(tmElements_t * tm); 139 | byte write(tmElements_t * tm); 140 | byte writeRTC(byte addr, byte *values, byte nBytes); 141 | byte writeRTC(byte addr, byte value); 142 | byte readRTC(byte addr, byte *values, byte nBytes); 143 | byte readRTC(byte addr); 144 | void setAlarm(ALARM_TYPES_t alarmType, byte seconds, byte minutes, byte hours, byte daydate); 145 | void setAlarm(ALARM_TYPES_t alarmType, byte minutes, byte hours, byte daydate); 146 | void alarmInterrupt(byte alarmNumber, bool alarmEnabled); 147 | bool alarm(byte alarmNumber); 148 | void squareWave(SQWAVE_FREQS_t freq); 149 | bool oscStopped(bool clearOSF = true); //defaults to clear the OSF bit if argument not supplied 150 | int temperature(void); 151 | 152 | uint8_t dt; 153 | }; 154 | 155 | extern DS3232RTC RTC; 156 | 157 | #endif 158 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/Wire.cpp: -------------------------------------------------------------------------------- 1 | 2 | 3 | #include "Wire.h" 4 | 5 | #include "ZUNO_Definitions.h" 6 | #include "ZUNO_call_proto.h" 7 | #include "ArduinoCAPI.h" 8 | 9 | 10 | 11 | #define STATE_TRANSMITION_INIT 0 12 | #define STATE_TRANSMITION_WRITEMODE 1 13 | #define STATE_TRANSMITION_READMODE 2 14 | #define STATE_TRANSMITION_STOPPED 3 15 | 16 | #define NACK_ON_ADDRESS 2 17 | #define NACK_ON_DATA 4 18 | 19 | #define FLAGS_REQSTOP 1 20 | 21 | 22 | 23 | 24 | 25 | 26 | // I2C Driver to use it with spins 27 | // AUXILARY CLASS 28 | I2CDriver::I2CDriver(s_pin scl, s_pin sda): _scl(scl), _sda(sda) 29 | { 30 | } 31 | void I2CDriver::bind(void) 32 | { 33 | pinMode(_scl, OUTPUT); 34 | pinMode(_sda, OUTPUT); 35 | digitalWrite(_scl, HIGH); 36 | digitalWrite(_sda, HIGH); 37 | } 38 | void I2CDriver::start(void) 39 | { 40 | noInterrupts(); 41 | NOPS(2); 42 | digitalWrite(_sda, LOW); 43 | NOPS(4); 44 | interrupts(); 45 | } 46 | void I2CDriver::stop(void) 47 | { 48 | noInterrupts(); 49 | digitalWrite(_scl, LOW); 50 | NOPS(2); 51 | pinMode(_sda, OUTPUT); 52 | digitalWrite(_sda, LOW); 53 | NOPS(8); 54 | digitalWrite(_scl, HIGH); 55 | NOPS(8); 56 | digitalWrite(_sda, HIGH); 57 | NOPS(8); 58 | interrupts(); 59 | } 60 | byte I2CDriver::write(byte b) 61 | { 62 | byte i = 8, ack; 63 | noInterrupts(); 64 | 65 | while(i) 66 | { 67 | digitalWrite(_scl, LOW); 68 | if( i == 8) 69 | { 70 | pinMode(_sda, OUTPUT); 71 | } 72 | else 73 | { 74 | NOPS(12); 75 | } 76 | NOPS(1); 77 | if(b & 0x80) 78 | digitalWrite(_sda, HIGH); 79 | else 80 | digitalWrite(_sda, LOW); 81 | //NOPS(1); 82 | digitalWrite(_scl, HIGH); 83 | NOPS(17); 84 | b <<= 1; 85 | i--; 86 | } 87 | 88 | // Принимаем ACK 89 | digitalWrite(_scl, LOW); 90 | pinMode(_sda, INPUT_PULLUP); 91 | NOPS(25); 92 | digitalWrite(_scl, HIGH); 93 | ack = digitalRead(_sda) == 0; 94 | 95 | NOPS(8); 96 | 97 | pinMode(_sda, OUTPUT); 98 | interrupts(); 99 | 100 | return ack; 101 | 102 | } 103 | 104 | byte I2CDriver::read(byte ack) 105 | { 106 | byte i = 8, input = 0; 107 | 108 | 109 | noInterrupts(); 110 | while(i) 111 | { 112 | 113 | digitalWrite(_scl, LOW); 114 | if(i==8) 115 | { 116 | pinMode(_sda, INPUT_PULLUP); 117 | } 118 | else 119 | { 120 | NOPS(14); 121 | } 122 | NOPS(17); 123 | digitalWrite(_scl, HIGH); 124 | input <<= 1; 125 | input |= digitalRead(_sda) > 0; 126 | NOPS(5); 127 | i--; 128 | } 129 | 130 | // Записываем ACK 131 | digitalWrite(_scl, LOW); 132 | NOPS(3); 133 | pinMode(_sda, OUTPUT); 134 | digitalWrite(_sda, LOW); 135 | if(!ack) 136 | digitalWrite(_sda, HIGH); 137 | NOPS(15); 138 | digitalWrite(_scl, HIGH); 139 | NOPS(18); 140 | interrupts(); 141 | 142 | return input; 143 | } 144 | 145 | // MAIN I2C CLASS 146 | TwoWire::TwoWire(I2CDriver * driver):p_driver(driver) 147 | { 148 | txAddress = 0; 149 | state = STATE_TRANSMITION_STOPPED; 150 | 151 | } 152 | void TwoWire::begin(I2CDriver * driver) 153 | { 154 | if(driver) 155 | { 156 | p_driver = driver; 157 | } 158 | 159 | p_driver->bind(); 160 | state = STATE_TRANSMITION_STOPPED; 161 | 162 | } 163 | void TwoWire::bindDriver(I2CDriver * driver) 164 | { 165 | p_driver = driver; 166 | } 167 | void TwoWire::beginTransmission(uint8_t addr, uint8_t forced_write) 168 | { 169 | txAddress = addr; 170 | 171 | 172 | // Подсоединяемся к шине I2C как мастер 173 | p_driver->start(); 174 | 175 | available_bytes = 1; // Пока так - нужно сделать нормальный интерфейс вызовов 176 | state = STATE_TRANSMITION_INIT; 177 | 178 | b_flags = 0; //FLAGS_REQSTOP; 179 | 180 | sucess_code = 0; 181 | 182 | if(forced_write) 183 | { 184 | sucess_code = p_driver->write(txAddress << 1); 185 | state = STATE_TRANSMITION_WRITEMODE; 186 | } 187 | 188 | } 189 | uint8_t TwoWire::endTransmission(uint8_t stop) 190 | { 191 | // Нужно для того, чтобы работал нормально скан шины и тд 192 | if(state == STATE_TRANSMITION_INIT) 193 | { 194 | if(!p_driver->write((txAddress << 1) | 0x01)) 195 | { 196 | sucess_code |= NACK_ON_ADDRESS; 197 | } 198 | } 199 | 200 | p_driver->stop(); 201 | 202 | state = STATE_TRANSMITION_STOPPED; 203 | 204 | return sucess_code; 205 | } 206 | uint8_t TwoWire::requestFrom(uint8_t addr, uint8_t count, bool stop) 207 | { 208 | txAddress = addr; 209 | 210 | available_bytes = count; 211 | 212 | if(stop) 213 | { 214 | b_flags |= FLAGS_REQSTOP; 215 | } 216 | // Arduino uses this function to start I2C connection sometimes 217 | if(state == STATE_TRANSMITION_STOPPED) 218 | { 219 | p_driver->start(); 220 | state = STATE_TRANSMITION_INIT; 221 | 222 | } 223 | if(state == STATE_TRANSMITION_INIT) 224 | { 225 | byte ret = p_driver->write((txAddress << 1) | (0x01)); 226 | state = STATE_TRANSMITION_READMODE; 227 | if(!ret) 228 | { 229 | sucess_code |= NACK_ON_ADDRESS; 230 | p_driver->stop(); 231 | state = STATE_TRANSMITION_STOPPED; 232 | available_bytes =0; 233 | return 0; 234 | } 235 | 236 | } 237 | 238 | 239 | 240 | return available_bytes; 241 | } 242 | size_t TwoWire::write(uint8_t data) 243 | { 244 | byte res; 245 | 246 | if(state == STATE_TRANSMITION_INIT) 247 | { 248 | 249 | res = p_driver->write(txAddress << 1); 250 | if(!res) 251 | { 252 | sucess_code |= NACK_ON_ADDRESS; 253 | return res; 254 | } 255 | state = STATE_TRANSMITION_WRITEMODE; 256 | 257 | } 258 | res = p_driver->write(data); 259 | if(!res) 260 | { 261 | sucess_code |= NACK_ON_DATA; 262 | } 263 | return res; 264 | } 265 | int TwoWire::available(void) 266 | { 267 | return available_bytes; 268 | } 269 | int TwoWire::read(void) 270 | { 271 | BYTE ret; 272 | BYTE b_ack = 1; 273 | if(state == STATE_TRANSMITION_STOPPED) 274 | return 0xFF; 275 | if(state == STATE_TRANSMITION_INIT) 276 | { 277 | ret = p_driver->write((txAddress << 1) | (0x01)); 278 | state = STATE_TRANSMITION_READMODE; 279 | if(!ret) 280 | { 281 | sucess_code |= NACK_ON_ADDRESS; 282 | p_driver->stop(); 283 | state = STATE_TRANSMITION_STOPPED; 284 | available_bytes =0; 285 | return 0; 286 | } 287 | 288 | } 289 | available_bytes--; 290 | if(!available_bytes) 291 | b_ack = 0; 292 | ret = p_driver->read(b_ack); 293 | 294 | if((!available_bytes) && (b_flags & FLAGS_REQSTOP)) 295 | { 296 | p_driver->stop(); 297 | state = STATE_TRANSMITION_STOPPED; 298 | } 299 | return ret; 300 | } 301 | int TwoWire::peek(void) 302 | { 303 | return 0; 304 | } 305 | void TwoWire::flush(void) 306 | { 307 | 308 | } 309 | I2CDriver defaultI2CDriver(SCL_PIN, SDA_PIN); 310 | TwoWire Wire(&defaultI2CDriver); 311 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/IRController.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2016 by Z-WAVE>ME (www.z-wave.me) for Z-Uno Project (z-uno.z-wave.me) 3 | * 4 | * Hardware IR-controller 5 | * 6 | * Adds ability to use built in IR controller in your Z-Uno projects 7 | * 8 | * All vendor-specific code was ported from IRremote library for Arduino 9 | * 10 | * INPUT of IR-Controller is PIN#7 11 | * OUTPUTS of IR-Controller are PIN#6,PIN#5,PIN#4 (You can use some pins to increase power, 8mA is max for one pin) 12 | * 13 | */ 14 | 15 | #pragma once 16 | 17 | #include "ArduinoTypes.h" 18 | #include "ZUNO_Definitions.h" 19 | 20 | 21 | enum 22 | { 23 | IR_VENDOR_AIWA, 24 | IR_VENDOR_DENON, 25 | IR_VENDOR_JVC, 26 | IR_VENDOR_LEGO, 27 | IR_VENDOR_LG, 28 | IR_VENDOR_MITSUBISHI, 29 | IR_VENDOR_NEC, 30 | IR_VENDOR_PANASONIC, 31 | IR_VENDOR_RC5, 32 | IR_VENDOR_RC6, 33 | IR_VENDOR_SAMSUNG, 34 | IR_VENDOR_SANYO, 35 | IR_VENDOR_SHARP, 36 | IR_VENDOR_SONY, 37 | IR_VENDOR_WHYNTER, 38 | 39 | 40 | IR_VENDOR_UNKNOWN = 0xFF 41 | 42 | }; 43 | // IR Receiver Settings and Values 44 | 45 | enum 46 | { 47 | IR_FLAGS_IO_INVERTED = 0x01, 48 | IR_FLAGS_OUTPUT_HIGHDRIVE = 0x02, 49 | IR_FLAGS_OUTPUT_MSCARRIER = 0x04, 50 | IR_FLAGS_OUTPUT_HIGHIDLE = 0x08, 51 | IR_FLAGS_INPUT_DETECTCARRIER = 0x10, 52 | IR_FLAGS_IO_OUTPUT = 0x80 53 | }; 54 | enum 55 | { 56 | IR_STATUS_BUF_OVERFLOW = 0x20, 57 | IR_STATUS_MARK_OVERFLOW = 0x10, 58 | IR_STATUS_CARRIER_FAILED = 0x08, 59 | IR_STATUS_DMA_FAILED = 0x02, 60 | IR_STATUS_BUSY = 0x01 61 | }; 62 | enum 63 | { 64 | IR_TRANSMITTER_OUTPUT_PIN6 = 0x1, 65 | IR_TRANSMITTER_OUTPUT_PIN5 = 0x2, 66 | IR_TRANSMITTER_OUTPUT_PIN4 = 0x4 67 | 68 | }; 69 | enum 70 | { 71 | IR_MS_PRESCALLER_32MHZ, // 0 72 | IR_MS_PRESCALLER_16MHZ, // 1 73 | IR_MS_PRESCALLER_8MHZ, // 2 74 | IR_MS_PRESCALLER_4MHZ, // 3 75 | IR_MS_PRESCALLER_2MHZ, // 4 76 | IR_MS_PRESCALLER_1MHZ, // 5 77 | IR_MS_PRESCALLER_500KHZ, 78 | IR_MS_PRESCALLER_250KHZ 79 | }; 80 | 81 | enum 82 | { 83 | IR_CARRIER_PRESCALLER_32MHZ, // 32 // 0 84 | IR_CARRIER_PRESCALLER_16MHZ, // 16 // 1 85 | IR_CARRIER_PRESCALLER_10P6MHZ, // 10.6 // 2 86 | IR_CARRIER_PRESCALLER_8MHZ, // 8 // 3 87 | IR_CARRIER_PRESCALLER_6P4MHZ, // 6.4 // 4 88 | IR_CARRIER_PRESCALLER_5P3MHZ, // 5.3 // 5 89 | IR_CARRIER_PRESCALLER_4P57MHZ, // 4.57 // 6 90 | IR_CARRIER_PRESCALLER_4MHZ // 4 // 7 91 | }; 92 | 93 | 94 | enum 95 | { 96 | IR_TRAILSPACE_05K, 97 | IR_TRAILSPACE_1K, 98 | IR_TRAILSPACE_2K, 99 | IR_TRAILSPACE_4K, 100 | IR_TRAILSPACE_8K, 101 | IR_TRAILSPACE_16K, 102 | IR_TRAILSPACE_32K, 103 | IR_TRAILSPACE_64K 104 | }; 105 | 106 | enum 107 | { 108 | IR_AVERAGER_1P, 109 | IR_AVERAGER_2P, 110 | IR_AVERAGER_4P, 111 | IR_AVERAGER_8P 112 | 113 | 114 | }; 115 | 116 | enum 117 | { 118 | IR_GLITCH_REMOVER_DISABLE, 119 | IR_GLITCH_REMOVER_125NS, 120 | IR_GLITCH_REMOVER_250NS, 121 | IR_GLITCH_REMOVER_500NS 122 | 123 | }; 124 | 125 | extern word g_ir_df; 126 | // IR-receiver settings 127 | class IRReceiverParams 128 | { 129 | public: 130 | 131 | IRReceiverParams(byte fl = 0, 132 | byte msp = IR_MS_PRESCALLER_2MHZ, 133 | byte crp = IR_MS_PRESCALLER_8MHZ, 134 | byte ts = IR_TRAILSPACE_16K, 135 | byte av = IR_AVERAGER_8P, 136 | byte gr = IR_GLITCH_REMOVER_500NS): 137 | flags(fl), 138 | ms_prescaller(msp), 139 | carrier_prescaller(crp), 140 | carrier_averagger(av), 141 | glitch_remover(gr), 142 | trail_space(ts) 143 | {}; 144 | // Vendor-specific constructor 145 | IRReceiverParams(int vendor, byte fl); 146 | 147 | public: 148 | byte getFlags(); 149 | byte getMSPrescaller(){return ms_prescaller;}; 150 | 151 | private: 152 | 153 | byte flags; 154 | byte ms_prescaller; 155 | byte carrier_prescaller; 156 | byte carrier_averagger; 157 | byte glitch_remover; 158 | byte trail_space; 159 | 160 | 161 | 162 | 163 | 164 | }; 165 | 166 | // IR-trasmitter settings 167 | class IRTransmitterParams 168 | { 169 | public: 170 | 171 | IRTransmitterParams(byte outputs = IR_TRANSMITTER_OUTPUT_PIN6, 172 | byte fl = 0, 173 | byte msp = IR_MS_PRESCALLER_1MHZ, 174 | byte crp = IR_MS_PRESCALLER_8MHZ, 175 | byte low = 74, byte high = 148): 176 | flags(fl | IR_FLAGS_IO_OUTPUT), 177 | ms_prescaller(msp), 178 | carrier_prescaller(crp), 179 | carrier_low(low), 180 | carrier_high(high), 181 | main_outputs(outputs) 182 | {}; 183 | 184 | public: 185 | byte getFlags(); 186 | byte getOutputs(){return main_outputs;}; 187 | byte getMSPrescaller(){return ms_prescaller;}; 188 | 189 | void setupVendor(int vendor); 190 | void setup_kHz(byte freq); 191 | 192 | private: 193 | 194 | byte flags; 195 | byte ms_prescaller; 196 | byte carrier_prescaller; 197 | byte carrier_low; 198 | byte carrier_high; 199 | byte main_outputs; 200 | 201 | 202 | 203 | }; 204 | 205 | #define MAX_IRCOMMAND_DATA 2 206 | 207 | typedef struct IRCommand_s 208 | { 209 | 210 | byte vendor; 211 | byte n_bits; 212 | unsigned long data[MAX_IRCOMMAND_DATA]; 213 | }IRCommand_t; 214 | 215 | // Main IR-Controller class 216 | class IRController 217 | { 218 | public: 219 | IRController(); 220 | // Start hardware IR controller as receiver 221 | void begin(IRReceiverParams * transmitter); 222 | void begin(IRTransmitterParams * receiver); 223 | 224 | // RAW16 format: 225 | // word # 1 2 3 4 5 ... N+1 226 | // NUMBER_OF_WORDS MARK#1 SPACE#1 MARK#2 SPACE#2 SPACE#N 227 | // all intervals in microseconds 228 | // the sequence always ends with mark 229 | 230 | // sends raw16-data via IR controller 231 | void send_raw16(word * data); 232 | // checks if raw16 data equals to current data received by ir 233 | bool equals_raw16(word * data); 234 | // receives raw16-data from IR controller 235 | void recv_raw16(word * data); 236 | 237 | // start/restart ir-scanning process 238 | void scan(); 239 | 240 | 241 | byte getState(); 242 | 243 | // try do detect IR VENDOR and parse command 244 | // return vedor_code see IR_VENDOR_* 245 | bool detectCommand(IRCommand_t * command); 246 | // Specific vendor version of previous method (helps to reduce memory if you know your vendor) 247 | bool readCommand_AIWA(IRCommand_t * command); 248 | bool readCommand_LG(IRCommand_t * command); 249 | bool readCommand_NEC(IRCommand_t * command); 250 | bool readCommand_PANASONIC(IRCommand_t * command); 251 | bool readCommand_RC5(IRCommand_t * command); 252 | bool readCommand_RC6(IRCommand_t* command); 253 | bool readCommand_SAMSUNG(IRCommand_t * command); 254 | bool readCommand_SONY(IRCommand_t * command); 255 | 256 | 257 | // sends ir-command using specified vendor encoding 258 | void sendCommand(IRCommand_t * command); 259 | // Specific vendor version of previous method (helps to reduce memory if you know your vendor) 260 | void sendCommand_AIWA(IRCommand_t * command); 261 | void sendCommand_LG(IRCommand_t * command); 262 | void sendCommand_NEC(IRCommand_t * command); 263 | void sendCommand_PANASONIC(IRCommand_t * command); 264 | void sendCommand_RC5(IRCommand_t * command); 265 | void sendCommand_RC6(IRCommand_t * command); 266 | void sendCommand_SAMSUNG(IRCommand_t * command); 267 | void sendCommand_SONY(IRCommand_t * command); 268 | 269 | // stops hardware IR-controller 270 | void end(); 271 | 272 | private: 273 | byte my_data; 274 | 275 | 276 | 277 | }; 278 | 279 | 280 | extern IRController IR; 281 | 282 | 283 | 284 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/Print.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | Print.cpp - Base class that provides print() and println() 3 | Copyright (c) 2008 David A. Mellis. All right reserved. 4 | 5 | This library is free software; you can redistribute it and/or 6 | modify it under the terms of the GNU Lesser General Public 7 | License as published by the Free Software Foundation; either 8 | version 2.1 of the License, or (at your option) any later version. 9 | 10 | This library is distributed in the hope that it will be useful, 11 | but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 13 | Lesser General Public License for more details. 14 | 15 | You should have received a copy of the GNU Lesser General Public 16 | License along with this library; if not, write to the Free Software 17 | Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 18 | 19 | Modified 23 November 2006 by David A. Mellis 20 | 21 | Simplified for Z-Uno project by Z-Wave.Me (c) 2016 22 | */ 23 | 24 | //#include 25 | //#include 26 | //#include "Arduino.h" 27 | 28 | #include "Print.h" 29 | 30 | #define JUST_NEW_LINE write('\r');write('\n'); 31 | #define NEW_LINE_ADDN 2 32 | 33 | 34 | size_t g_n; 35 | uint8_t g_i; 36 | //word g_write_counter2 = 0; 37 | /// 38 | 39 | // Public Methods ////////////////////////////////////////////////////////////// 40 | 41 | /* default implementation: may be overridden */ 42 | size_t Print::write(uint8_t *buffer, size_t size) 43 | { 44 | g_n = size; 45 | while (size--) { 46 | write(*buffer++); 47 | } 48 | return g_n; 49 | } 50 | 51 | size_t Print::print(char * str) 52 | { 53 | 54 | for(g_i=0;g_i<0xff;g_i++) 55 | { 56 | if(str[g_i] == 0) 57 | break; 58 | write(str[g_i]); 59 | } 60 | return g_i; 61 | 62 | } 63 | 64 | size_t Print::print(char c) 65 | { 66 | return write(c); 67 | } 68 | 69 | size_t Print::print(unsigned char b, int base) 70 | { 71 | return printNumber((unsigned long)b, base); 72 | } 73 | 74 | size_t Print::print(int n, int base) 75 | { 76 | byte add_sz = 0; 77 | if (base == 0) 78 | return write(n); 79 | if ((base == 10) && (n < 0)) 80 | { 81 | n = -n; 82 | write('-'); 83 | add_sz=1; 84 | } 85 | 86 | return printNumber(((unsigned long)n)&0xFFFF, base) + add_sz; 87 | } 88 | 89 | size_t Print::print(unsigned int n, int base) 90 | { 91 | return print(((unsigned long) n) & 0xFFFF, base); 92 | } 93 | 94 | size_t Print::print(long n, int base) 95 | { 96 | byte add_sz = 0; 97 | if (base == 0) 98 | return write(n); 99 | if ((base == 10) && (n < 0)) 100 | { 101 | n = -n; 102 | write('-'); 103 | add_sz=1; 104 | } 105 | 106 | return printNumber(n, base) + add_sz; 107 | 108 | } 109 | 110 | size_t Print::print(unsigned long n, int base) 111 | { 112 | if (base == 0) 113 | return write(n); 114 | return printNumber(n, base); 115 | 116 | } 117 | 118 | size_t Print::print(float n, int digits) 119 | { 120 | return printFloat(n, digits); 121 | } 122 | size_t Print::print(double n, int digits) 123 | { 124 | return printFloat((double)n, digits); 125 | } 126 | size_t Print::println(void) 127 | { 128 | JUST_NEW_LINE; 129 | return NEW_LINE_ADDN; 130 | } 131 | 132 | size_t Print::println(char * c) 133 | { 134 | 135 | // Упрощенный код 136 | // --------------- 137 | //byte i; 138 | //for(i=0;i<100;i++) 139 | //{ 140 | // if(c[i] == 0) 141 | // return i; 142 | // write(c[i]); 143 | //} 144 | print(c); 145 | JUST_NEW_LINE; 146 | return g_n+NEW_LINE_ADDN; 147 | 148 | //return 100; 149 | // --------------- 150 | // код из Arduino 151 | //size_t n = print(c); 152 | //n += println(); 153 | // return n; 154 | 155 | } 156 | 157 | size_t Print::println(char c) 158 | { 159 | write(c); 160 | JUST_NEW_LINE; 161 | return 1+NEW_LINE_ADDN; 162 | } 163 | 164 | size_t Print::println(unsigned char b, int base) 165 | { 166 | print(b, base); 167 | JUST_NEW_LINE; 168 | return g_n+NEW_LINE_ADDN; 169 | } 170 | 171 | size_t Print::println(int num, int base) 172 | { 173 | print(num, base); 174 | JUST_NEW_LINE; 175 | return g_n+NEW_LINE_ADDN; 176 | } 177 | 178 | size_t Print::println(unsigned int num, int base) 179 | { 180 | print(num, base); 181 | JUST_NEW_LINE; 182 | return g_n+NEW_LINE_ADDN; 183 | } 184 | 185 | size_t Print::println(long num, int base) 186 | { 187 | print(num, base); 188 | JUST_NEW_LINE; 189 | return g_n+NEW_LINE_ADDN; 190 | } 191 | 192 | size_t Print::println(unsigned long num, int base) 193 | { 194 | print(num, base); 195 | JUST_NEW_LINE; 196 | return g_n+NEW_LINE_ADDN; 197 | } 198 | 199 | size_t Print::println(float num, int digits) 200 | { 201 | printFloat(num, digits); 202 | JUST_NEW_LINE; 203 | return g_n+NEW_LINE_ADDN; 204 | } 205 | size_t Print::println(double num, int digits) 206 | { 207 | printFloat((float)num, digits); 208 | JUST_NEW_LINE; 209 | return g_n+NEW_LINE_ADDN; 210 | } 211 | // Private Methods ///////////////////////////////////////////////////////////// 212 | 213 | uint8_t g_digit_buffer[32]; 214 | uint8_t g_digit_len = 0; 215 | 216 | unsigned long g_long_tmp = 0; 217 | float g_float_tmp = 0; 218 | 219 | 220 | 221 | size_t Print::printNumber(unsigned long n, uint8_t base) { 222 | 223 | g_digit_len = 0; 224 | 225 | // prevent crash if called with base == 1 226 | if (base < 2) base = 10; 227 | 228 | do 229 | { 230 | g_i = n % base; 231 | n /= base; 232 | g_digit_buffer[g_digit_len++] = g_i < 10 ? g_i + '0' : g_i + 'A' - 10; 233 | } while(n); 234 | 235 | 236 | g_n = g_digit_len; 237 | 238 | // Печатаем в обратном порядке 239 | while(g_digit_len--) 240 | write(g_digit_buffer[g_digit_len]); 241 | 242 | return g_n; 243 | } 244 | 245 | /* 246 | 247 | size_t Print::printByteArr(uint8_t * bytearr, uint8_t len, uint8_t base) { 248 | 249 | uint8_t i; 250 | uint8_t num; 251 | char c; 252 | uint8_t have_one_non_zero = false; 253 | 254 | g_n = 0; 255 | 256 | 257 | 258 | 259 | // prevent crash if called with base == 1 260 | if (base < 2) base = 10; 261 | 262 | // На всякий случай! 263 | g_digit_len = 0; 264 | 265 | for(g_i=0; g_i 0) { 325 | g_n++; 326 | write('.'); 327 | } 328 | 329 | // Extract digits from the remainder one at a time 330 | while (digits-- > 0) 331 | { 332 | g_float_tmp *= 10.0; 333 | g_digit_buffer[0] = uint8_t(g_float_tmp); 334 | write('0'+ g_digit_buffer[0]); 335 | g_n++; 336 | g_float_tmp -= g_digit_buffer[0]; 337 | } 338 | 339 | return g_n; 340 | } 341 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_BMP180/ZUNO_BMP180.cpp: -------------------------------------------------------------------------------- 1 | /*************************************************** 2 | This is a library for the Adafruit BMP085/BMP180 Barometric Pressure + Temp sensor 3 | 4 | Designed specifically to work with the Adafruit BMP085 or BMP180 Breakout 5 | ----> http://www.adafruit.com/products/391 6 | ----> http://www.adafruit.com/products/1603 7 | 8 | These displays use I2C to communicate, 2 pins are required to 9 | interface 10 | Adafruit invests time and resources providing this open source code, 11 | please support Adafruit and open-source hardware by purchasing 12 | products from Adafruit! 13 | 14 | Written by Limor Fried/Ladyada for Adafruit Industries. 15 | BSD license, all text above must be included in any redistribution 16 | ****************************************************/ 17 | 18 | #include "ZUNO_BMP180.h" 19 | #include "Wire.h" 20 | 21 | 22 | #define BMP180_DEBUG 0 23 | 24 | 25 | #define DEBUG_SERIAL Serial1 26 | 27 | 28 | #define _delay_ms(d) delay(d) 29 | 30 | ZUNO_BMP180::ZUNO_BMP180() { 31 | } 32 | 33 | 34 | boolean ZUNO_BMP180::begin(uint8_t mode) { 35 | if (mode > BMP085_ULTRAHIGHRES) 36 | mode = BMP085_ULTRAHIGHRES; 37 | oversampling = mode; 38 | 39 | Wire.begin(); 40 | 41 | if (read8(0xD0) != 0x55) return false; 42 | 43 | /* read calibration data */ 44 | ac1 = read16(BMP085_CAL_AC1); 45 | ac2 = read16(BMP085_CAL_AC2); 46 | ac3 = read16(BMP085_CAL_AC3); 47 | ac4 = read16(BMP085_CAL_AC4); 48 | ac5 = read16(BMP085_CAL_AC5); 49 | ac6 = read16(BMP085_CAL_AC6); 50 | 51 | b1 = read16(BMP085_CAL_B1); 52 | b2 = read16(BMP085_CAL_B2); 53 | 54 | mb = read16(BMP085_CAL_MB); 55 | mc = read16(BMP085_CAL_MC); 56 | md = read16(BMP085_CAL_MD); 57 | 58 | } 59 | void ZUNO_BMP180::dumpInternal() 60 | { 61 | DEBUG_SERIAL.println("--- BMP180 parameters ---"); 62 | DEBUG_SERIAL.print("ac1 = "); DEBUG_SERIAL.print(ac1, DEC); DEBUG_SERIAL.print(" HEX:"); DEBUG_SERIAL.println(ac1, HEX); 63 | DEBUG_SERIAL.print("ac2 = "); DEBUG_SERIAL.print(ac2, DEC); DEBUG_SERIAL.print(" HEX:"); DEBUG_SERIAL.println(ac2, HEX); 64 | DEBUG_SERIAL.print("ac3 = "); DEBUG_SERIAL.print(ac3, DEC); DEBUG_SERIAL.print(" HEX:"); DEBUG_SERIAL.println(ac3, HEX); 65 | DEBUG_SERIAL.print("ac4 = "); DEBUG_SERIAL.print((unsigned int)ac4, DEC); DEBUG_SERIAL.print(" HEX:"); DEBUG_SERIAL.println(ac4, HEX); 66 | DEBUG_SERIAL.print("ac5 = "); DEBUG_SERIAL.print((unsigned int)ac5, DEC); DEBUG_SERIAL.print(" HEX:"); DEBUG_SERIAL.println(ac5, HEX); 67 | DEBUG_SERIAL.print("ac6 = "); DEBUG_SERIAL.print((unsigned int)ac6, DEC); DEBUG_SERIAL.print(" HEX:"); DEBUG_SERIAL.println(ac6, HEX); 68 | 69 | DEBUG_SERIAL.print("b1 = "); DEBUG_SERIAL.print(b1, DEC); DEBUG_SERIAL.print(" HEX:"); DEBUG_SERIAL.println(b1, HEX); 70 | DEBUG_SERIAL.print("b2 = "); DEBUG_SERIAL.print(b2, DEC); DEBUG_SERIAL.print(" HEX:"); DEBUG_SERIAL.println(b2, HEX); 71 | 72 | DEBUG_SERIAL.print("mb = "); DEBUG_SERIAL.print(mb, DEC); DEBUG_SERIAL.print(" HEX:"); DEBUG_SERIAL.println(mb, HEX); 73 | 74 | DEBUG_SERIAL.print("mc = "); DEBUG_SERIAL.print(mc, DEC); DEBUG_SERIAL.print(" HEX:"); DEBUG_SERIAL.println(mc, HEX); 75 | DEBUG_SERIAL.print("md = "); DEBUG_SERIAL.print(md, DEC); DEBUG_SERIAL.print(" HEX:"); DEBUG_SERIAL.println(md, HEX); 76 | DEBUG_SERIAL.println("--- ****************** ---"); 77 | 78 | } 79 | uint16_t ZUNO_BMP180::readRawTemperature(void) { 80 | write8(BMP085_CONTROL, BMP085_READTEMPCMD); 81 | _delay_ms(5); 82 | return read16(BMP085_TEMPDATA); 83 | } 84 | 85 | uint32_t ZUNO_BMP180::readRawPressure(void) { 86 | uint32_t raw; 87 | 88 | write8(BMP085_CONTROL, BMP085_READPRESSURECMD + (oversampling << 6)); 89 | 90 | if (oversampling == BMP085_ULTRALOWPOWER) 91 | _delay_ms(5); 92 | else if (oversampling == BMP085_STANDARD) 93 | _delay_ms(8); 94 | else if (oversampling == BMP085_HIGHRES) 95 | _delay_ms(14); 96 | else 97 | _delay_ms(26); 98 | 99 | raw = read16(BMP085_PRESSUREDATA); 100 | 101 | raw <<= 8; 102 | raw |= read8(BMP085_PRESSUREDATA+2); 103 | raw >>= (8 - oversampling); 104 | 105 | 106 | return raw; 107 | } 108 | 109 | 110 | int32_t ZUNO_BMP180::readPressure(void) { 111 | 112 | int16_t UT = readRawTemperature(); 113 | long UP = readRawPressure(); 114 | 115 | 116 | long X1 = UT - ac6; 117 | long X2 = mc; 118 | 119 | X1 *= ac5; 120 | X1 >>= 15; 121 | X2 <<= 11; 122 | X2 /= (X1 + md); 123 | //1) => B5 => B6 124 | long B6 = (X1 + X2) - 4000; 125 | #if BMP180_DEBUG 126 | DEBUG_SERIAL.print("B6 = "); DEBUG_SERIAL.println(B6, DEC); ; 127 | #endif 128 | 129 | //2) X1 130 | // X1 = (B2*(B6*B6)/2^12)/2^11 131 | X2 = X1 = B6; 132 | X1 *= B6; 133 | X1 >>= 12; 134 | uint16_t koef1 = X1; 135 | X1 *= b2; 136 | X1 >>= 11; 137 | //3) 138 | // X2 = ac2*b6/2^11 139 | X2 *= ac2; 140 | X2 >>= 11; 141 | // 4 142 | // B3 = ((4*ac1 + X1 + X2)*2^(oversampling) + 2) / 4 143 | long B3 = ac1; 144 | B3 <<= 2; 145 | B3 += X1 + X2; 146 | B3 <<= oversampling; 147 | B3 >>= 2; 148 | #if BMP180_DEBUG 149 | DEBUG_SERIAL.print("B3 = "); DEBUG_SERIAL.println(B3, DEC); ; 150 | #endif 151 | 152 | // 5) 153 | // X1 = AC3*B6/2^13 154 | X1 = ac3; 155 | X1 *= B6; 156 | X1 >>= 13; 157 | // 6) 158 | // X2 = (b1*b6*b6/2^12)/2^16 159 | X2 = b1; 160 | X2 *= koef1; 161 | X2 >>= 16; 162 | // 163 | X1 += X2 + 2; 164 | X1 >>= 2; 165 | 166 | // B4.... 167 | unsigned long B4 = X1; 168 | B4 += 32768; 169 | B4 *= ac4; 170 | B4 >>= 15; 171 | #if BMP180_DEBUG 172 | DEBUG_SERIAL.print("B4 = "); DEBUG_SERIAL.println(B4, DEC); 173 | #endif 174 | 175 | 176 | 177 | // B7 178 | unsigned long B7 = UP-B3; // B7 179 | B7 *= (50000 >> oversampling); 180 | 181 | #if BMP180_DEBUG 182 | DEBUG_SERIAL.print("B7 = "); DEBUG_SERIAL.println(B7, DEC); 183 | #endif 184 | 185 | 186 | long p = (B7 & 0x80000000) ? (B7/B4) << 1 : (B7 << 1) / B4 ; 187 | 188 | #if BMP180_DEBUG 189 | DEBUG_SERIAL.print("p = "); DEBUG_SERIAL.println(p, DEC); 190 | #endif 191 | 192 | 193 | X1 = p >> 8; 194 | X1 *= X1; 195 | X1 *= 3038; 196 | X1 >>= 16; 197 | X2 = p; 198 | X2 *= -7357; 199 | X2 >>= 16; 200 | X1 += X2 + 3791; 201 | X1 >>= 4; 202 | 203 | p += X1; 204 | 205 | return p; 206 | } 207 | 208 | 209 | int16_t ZUNO_BMP180::readTemperatureC10(void) { 210 | 211 | 212 | int16_t UT = readRawTemperature(); 213 | //Serial.print("UT="); 214 | //Serial.println(UT); 215 | long X1 = UT - ac6; 216 | long X2 = mc; 217 | 218 | X1 *= ac5; 219 | X1 >>= 15; 220 | X2 <<= 11; 221 | X2 /= (X1 + md); 222 | X1 += X2 + 8; 223 | X1 >>= 4; 224 | 225 | return (int16_t) X1; 226 | } 227 | 228 | float ZUNO_BMP180::readTemperature(void) 229 | { 230 | return readTemperatureC10() / 10.0; 231 | } 232 | float ZUNO_BMP180::readAltitude(float sealevelPressure) { 233 | float altitude; 234 | 235 | float pressure = readPressure(); 236 | 237 | altitude = 44330 * (1.0 - pow(pressure /sealevelPressure,0.1903)); 238 | 239 | return altitude; 240 | } 241 | 242 | 243 | /*********************************************************************/ 244 | 245 | uint8_t ZUNO_BMP180::read8(uint8_t a) { 246 | uint8_t ret; 247 | 248 | Wire.beginTransmission(BMP085_I2CADDR); // start transmission to device 249 | Wire.write(a); // sends register address to read from 250 | Wire.endTransmission(); // end transmission 251 | 252 | //Wire.beginTransmission(BMP085_I2CADDR); // start transmission to device 253 | Wire.requestFrom(BMP085_I2CADDR, 1);// send data n-bytes read 254 | ret = Wire.read(); // receive DATA 255 | //Wire.endTransmission(); // end transmission 256 | 257 | return ret; 258 | } 259 | 260 | uint16_t ZUNO_BMP180::read16(uint8_t a) { 261 | uint16_t ret; 262 | 263 | Wire.beginTransmission(BMP085_I2CADDR); // start transmission to device 264 | Wire.write(a); // sends register address to read from 265 | Wire.endTransmission(); // end transmission 266 | 267 | //Wire.beginTransmission(BMP085_I2CADDR); // start transmission to device 268 | Wire.requestFrom(BMP085_I2CADDR, 2);// send data n-bytes read 269 | ret = Wire.read(); // receive DATA 270 | ret <<= 8; 271 | ret |= Wire.read(); // receive DATA 272 | //Wire.endTransmission(); // end transmission 273 | 274 | return ret; 275 | } 276 | 277 | void ZUNO_BMP180::write8(uint8_t a, uint8_t d) { 278 | Wire.beginTransmission(BMP085_I2CADDR); // start transmission to device 279 | Wire.write(a); // sends register address to read from 280 | Wire.write(d); // write data 281 | Wire.endTransmission(); // end transmission 282 | } 283 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_MCP23017/ZUNO_MCP23017.cpp: -------------------------------------------------------------------------------- 1 | /*************************************************** 2 | This is a library for the MCP23017 i2c port expander 3 | 4 | These displays use I2C to communicate, 2 pins are required to 5 | interface 6 | Adafruit invests time and resources providing this open source code, 7 | please support Adafruit and open-source hardware by purchasing 8 | products from Adafruit! 9 | 10 | Written by Limor Fried/Ladyada for Adafruit Industries. 11 | BSD license, all text above must be included in any redistribution 12 | 13 | Adoptated for Z-Uno project by Z-Wave>ME 2016 14 | ****************************************************/ 15 | 16 | 17 | 18 | #include 19 | #include "ZUNO_MCP23017.h" 20 | #include "Arduino.h" 21 | 22 | #define wiresend(x) Wire.write((uint8_t) x) 23 | #define wirerecv() Wire.read() 24 | 25 | /** 26 | * Bit number associated to a give Pin 27 | */ 28 | uint8_t ZUNO_MCP23017::bitForPin(uint8_t pin){ 29 | return pin%8; 30 | } 31 | 32 | /** 33 | * Register address, port dependent, for a given PIN 34 | */ 35 | uint8_t ZUNO_MCP23017::regForPin(uint8_t pin, uint8_t portAaddr, uint8_t portBaddr){ 36 | return(pin<8) ?portAaddr:portBaddr; 37 | } 38 | 39 | /** 40 | * Reads a given register 41 | */ 42 | uint8_t ZUNO_MCP23017::readRegister(uint8_t addr){ 43 | // read the current GPINTEN 44 | Wire.beginTransmission(MCP23017_ADDRESS | i2caddr); 45 | wiresend(addr); 46 | Wire.endTransmission(); 47 | Wire.requestFrom(MCP23017_ADDRESS | i2caddr, 1); 48 | return wirerecv(); 49 | } 50 | 51 | 52 | /** 53 | * Writes a given register 54 | */ 55 | void ZUNO_MCP23017::writeRegister(uint8_t regAddr, uint8_t regValue){ 56 | // Write the register 57 | Wire.beginTransmission(MCP23017_ADDRESS | i2caddr); 58 | wiresend(regAddr); 59 | wiresend(regValue); 60 | Wire.endTransmission(); 61 | } 62 | 63 | 64 | /** 65 | * Helper to update a single bit of an A/B register. 66 | * - Reads the current register value 67 | * - Writes the new register value 68 | */ 69 | void ZUNO_MCP23017::updateRegisterBit(uint8_t pin, uint8_t pValue, uint8_t portAaddr, uint8_t portBaddr) { 70 | uint8_t regValue; 71 | uint8_t regAddr=regForPin(pin,portAaddr,portBaddr); 72 | uint8_t bit=bitForPin(pin); 73 | regValue = readRegister(regAddr); 74 | 75 | // set the value for the particular bit 76 | bitWrite(regValue,bit,pValue); 77 | 78 | writeRegister(regAddr,regValue); 79 | } 80 | 81 | //////////////////////////////////////////////////////////////////////////////// 82 | 83 | /** 84 | * Initializes the MCP23017 given its HW selected address, see datasheet for Address selection. 85 | */ 86 | void ZUNO_MCP23017::begin(uint8_t addr) { 87 | if (addr > 7) { 88 | addr = 7; 89 | } 90 | i2caddr = addr; 91 | 92 | Wire.begin(); 93 | 94 | // set defaults! 95 | // all inputs on port A and B 96 | writeRegister(MCP23017_IODIRA,0xff); 97 | writeRegister(MCP23017_IODIRB,0xff); 98 | } 99 | 100 | /** 101 | * Initializes the default MCP23017, with 000 for the configurable part of the address 102 | */ 103 | void ZUNO_MCP23017::begin(void) { 104 | begin(0); 105 | } 106 | 107 | /** 108 | * Sets the pin mode to either INPUT or OUTPUT 109 | */ 110 | void ZUNO_MCP23017::pinMode(uint8_t p, uint8_t d) { 111 | updateRegisterBit(p,(d==INPUT),MCP23017_IODIRA,MCP23017_IODIRB); 112 | } 113 | 114 | /** 115 | * Reads all 16 pins (port A and B) into a single 16 bits variable. 116 | */ 117 | uint16_t ZUNO_MCP23017::readGPIOAB() { 118 | uint16_t ba = 0; 119 | uint8_t a; 120 | 121 | // read the current GPIO output latches 122 | Wire.beginTransmission(MCP23017_ADDRESS | i2caddr); 123 | wiresend(MCP23017_GPIOA); 124 | Wire.endTransmission(); 125 | 126 | Wire.requestFrom(MCP23017_ADDRESS | i2caddr, 2); 127 | a = wirerecv(); 128 | ba = wirerecv(); 129 | ba <<= 8; 130 | ba |= a; 131 | 132 | return ba; 133 | } 134 | 135 | /** 136 | * Read a single port, A or B, and return its current 8 bit value. 137 | * Parameter b should be 0 for GPIOA, and 1 for GPIOB. 138 | */ 139 | uint8_t ZUNO_MCP23017::readGPIO(uint8_t b) { 140 | 141 | // read the current GPIO output latches 142 | Wire.beginTransmission(MCP23017_ADDRESS | i2caddr); 143 | if (b == 0) 144 | wiresend(MCP23017_GPIOA); 145 | else { 146 | wiresend(MCP23017_GPIOB); 147 | } 148 | Wire.endTransmission(); 149 | 150 | Wire.requestFrom(MCP23017_ADDRESS | i2caddr, 1); 151 | return wirerecv(); 152 | } 153 | 154 | /** 155 | * Writes all the pins in one go. This method is very useful if you are implementing a multiplexed matrix and want to get a decent refresh rate. 156 | */ 157 | void ZUNO_MCP23017::writeGPIOAB(uint16_t ba) { 158 | Wire.beginTransmission(MCP23017_ADDRESS | i2caddr); 159 | wiresend(MCP23017_GPIOA); 160 | wiresend(ba & 0xFF); 161 | wiresend(ba >> 8); 162 | Wire.endTransmission(); 163 | } 164 | 165 | void ZUNO_MCP23017::digitalWrite(uint8_t pin, uint8_t d) { 166 | uint8_t gpio; 167 | uint8_t bit=bitForPin(pin); 168 | 169 | 170 | // read the current GPIO output latches 171 | uint8_t regAddr=regForPin(pin,MCP23017_OLATA,MCP23017_OLATB); 172 | gpio = readRegister(regAddr); 173 | 174 | // set the pin and direction 175 | bitWrite(gpio,bit,d); 176 | 177 | // write the new GPIO 178 | regAddr=regForPin(pin,MCP23017_GPIOA,MCP23017_GPIOB); 179 | writeRegister(regAddr,gpio); 180 | } 181 | 182 | void ZUNO_MCP23017::pullUp(uint8_t p, uint8_t d) { 183 | updateRegisterBit(p,d,MCP23017_GPPUA,MCP23017_GPPUB); 184 | } 185 | 186 | uint8_t ZUNO_MCP23017::digitalRead(uint8_t pin) { 187 | uint8_t bit=bitForPin(pin); 188 | uint8_t regAddr=regForPin(pin,MCP23017_GPIOA,MCP23017_GPIOB); 189 | return (readRegister(regAddr) >> bit) & 0x1; 190 | } 191 | 192 | /** 193 | * Configures the interrupt system. both port A and B are assigned the same configuration. 194 | * Mirroring will OR both INTA and INTB pins. 195 | * Opendrain will set the INT pin to value or open drain. 196 | * polarity will set LOW or HIGH on interrupt. 197 | * Default values after Power On Reset are: (false,flase, LOW) 198 | * If you are connecting the INTA/B pin to arduino 2/3, you should configure the interupt handling as FALLING with 199 | * the default configuration. 200 | */ 201 | void ZUNO_MCP23017::setupInterrupts(uint8_t mirroring, uint8_t openDrain, uint8_t polarity){ 202 | // configure the port A 203 | uint8_t ioconfValue=readRegister(MCP23017_IOCONA); 204 | bitWrite(ioconfValue,6,mirroring); 205 | bitWrite(ioconfValue,2,openDrain); 206 | bitWrite(ioconfValue,1,polarity); 207 | writeRegister(MCP23017_IOCONA,ioconfValue); 208 | 209 | // Configure the port B 210 | ioconfValue=readRegister(MCP23017_IOCONB); 211 | bitWrite(ioconfValue,6,mirroring); 212 | bitWrite(ioconfValue,2,openDrain); 213 | bitWrite(ioconfValue,1,polarity); 214 | writeRegister(MCP23017_IOCONB,ioconfValue); 215 | } 216 | 217 | /** 218 | * Set's up a pin for interrupt. uses arduino MODEs: CHANGE, FALLING, RISING. 219 | * 220 | * Note that the interrupt condition finishes when you read the information about the port / value 221 | * that caused the interrupt or you read the port itself. Check the datasheet can be confusing. 222 | * 223 | */ 224 | void ZUNO_MCP23017::setupInterruptPin(uint8_t pin, uint8_t mode) { 225 | 226 | // set the pin interrupt control (0 means change, 1 means compare against given value); 227 | updateRegisterBit(pin,(mode!=CHANGE),MCP23017_INTCONA,MCP23017_INTCONB); 228 | // if the mode is not CHANGE, we need to set up a default value, different value triggers interrupt 229 | 230 | // In a RISING interrupt the default value is 0, interrupt is triggered when the pin goes to 1. 231 | // In a FALLING interrupt the default value is 1, interrupt is triggered when pin goes to 0. 232 | updateRegisterBit(pin,(mode==FALLING),MCP23017_DEFVALA,MCP23017_DEFVALB); 233 | 234 | // enable the pin for interrupt 235 | updateRegisterBit(pin,HIGH,MCP23017_GPINTENA,MCP23017_GPINTENB); 236 | 237 | } 238 | 239 | uint8_t ZUNO_MCP23017::getLastInterruptPin(){ 240 | uint8_t intf; 241 | 242 | // try port A 243 | intf=readRegister(MCP23017_INTFA); 244 | for(int i=0;i<8;i++) if (bitRead(intf,i)) return i; 245 | 246 | // try port B 247 | intf=readRegister(MCP23017_INTFB); 248 | for(int i=0;i<8;i++) if (bitRead(intf,i)) return i+8; 249 | 250 | return MCP23017_INT_ERR; 251 | 252 | } 253 | uint8_t ZUNO_MCP23017::getLastInterruptPinValue(){ 254 | uint8_t intPin=getLastInterruptPin(); 255 | if(intPin!=MCP23017_INT_ERR){ 256 | uint8_t intcapreg=regForPin(intPin,MCP23017_INTCAPA,MCP23017_INTCAPB); 257 | uint8_t bit=bitForPin(intPin); 258 | return (readRegister(intcapreg)>>bit) & (0x01); 259 | } 260 | 261 | return MCP23017_INT_ERR; 262 | } 263 | 264 | 265 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/cores/zuno/Stream.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | Stream.cpp - adds parsing methods to Stream class 3 | Copyright (c) 2008 David A. Mellis. All right reserved. 4 | 5 | This library is free software; you can redistribute it and/or 6 | modify it under the terms of the GNU Lesser General Public 7 | License as published by the Free Software Foundation; either 8 | version 2.1 of the License, or (at your option) any later version. 9 | 10 | This library is distributed in the hope that it will be useful, 11 | but WITHOUT ANY WARRANTY; without even the implied warranty of 12 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 13 | Lesser General Public License for more details. 14 | 15 | You should have received a copy of the GNU Lesser General Public 16 | License along with this library; if not, write to the Free Software 17 | Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 18 | 19 | Created July 2011 20 | parsing functions based on TextFinder library by Michael Margolis 21 | 22 | findMulti/findUntil routines written by Jim Leonard/Xuth 23 | */ 24 | 25 | #include "Stream.h" 26 | #include "ArduinoCAPI.h" 27 | 28 | 29 | #define PARSE_TIMEOUT 1000 // default number of milli-seconds to wait 30 | #define NO_SKIP_CHAR 1 // a magic char not found in a valid ASCII numeric field 31 | 32 | // private method to read stream with timeout 33 | int Stream::timedRead() 34 | { 35 | int c; 36 | _startMillis = millis(); 37 | do { 38 | c = read(); 39 | if (c >= 0) return c; 40 | } while(millis() - _startMillis < _timeout); 41 | return -1; // -1 indicates timeout 42 | } 43 | 44 | // private method to peek stream with timeout 45 | int Stream::timedPeek() 46 | { 47 | int c; 48 | _startMillis = millis(); 49 | do { 50 | c = peek(); 51 | if (c >= 0) return c; 52 | } while(millis() - _startMillis < _timeout); 53 | return -1; // -1 indicates timeout 54 | } 55 | 56 | // returns peek of the next digit in the stream or -1 if timeout 57 | // discards non-numeric characters 58 | int Stream::peekNextDigit() 59 | { 60 | int c; 61 | while (1) { 62 | c = timedPeek(); 63 | if (c < 0) return c; // timeout 64 | if (c == '-') return c; 65 | if (c >= '0' && c <= '9') return c; 66 | read(); // discard non-numeric 67 | } 68 | } 69 | 70 | // Public Methods 71 | ////////////////////////////////////////////////////////////// 72 | 73 | void Stream::setTimeout(unsigned long timeout) // sets the maximum number of milliseconds to wait 74 | { 75 | _timeout = timeout; 76 | } 77 | 78 | // find returns true if the target string is found 79 | bool Stream::find(char *target) 80 | { 81 | return findUntil(target, strlen(target), (char*)0, 0); 82 | } 83 | 84 | // reads data from the stream until the target string of given length is found 85 | // returns true if target string is found, false if timed out 86 | bool Stream::find(char *target, size_t length) 87 | { 88 | return findUntil(target, length, (char*)0, 0); 89 | } 90 | 91 | // as find but search ends if the terminator string is found 92 | bool Stream::findUntil(char *target, char *terminator) 93 | { 94 | return findUntil(target, strlen(target), terminator, strlen(terminator)); 95 | } 96 | 97 | // reads data from the stream until the target string of the given length is found 98 | // search terminated if the terminator string is found 99 | // returns true if target string is found, false if terminated or timed out 100 | bool Stream::findUntil(char *target, size_t targetLen, char *terminator, size_t termLen) 101 | { 102 | if (!terminator) { 103 | MultiTarget t[1] = {{target, targetLen, 0}}; 104 | return findMulti(t, 1) == 0 ? true : false; 105 | } else { 106 | MultiTarget t[2] = {{target, targetLen, 0}, {terminator, termLen, 0}}; 107 | return findMulti(t, 2) == 0 ? true : false; 108 | } 109 | } 110 | 111 | 112 | // returns the first valid (long) integer value from the current position. 113 | // initial characters that are not digits (or the minus sign) are skipped 114 | // function is terminated by the first character that is not a digit. 115 | long Stream::parseInt() 116 | { 117 | return parseInt(NO_SKIP_CHAR); // terminate on first non-digit character (or timeout) 118 | } 119 | 120 | // as above but a given skipChar is ignored 121 | // this allows format characters (typically commas) in values to be ignored 122 | long Stream::parseInt(char skipChar) 123 | { 124 | bool isNegative = false; 125 | long value = 0; 126 | int c; 127 | 128 | c = peekNextDigit(); 129 | // ignore non numeric leading characters 130 | if(c < 0) 131 | return 0; // zero returned if timeout 132 | 133 | do{ 134 | if(c == skipChar) 135 | ; // ignore this charactor 136 | else if(c == '-') 137 | isNegative = true; 138 | else if(c >= '0' && c <= '9') // is c a digit? 139 | value = value * 10 + c - '0'; 140 | read(); // consume the character we got with peek 141 | c = timedPeek(); 142 | } 143 | while( (c >= '0' && c <= '9') || c == skipChar ); 144 | 145 | if(isNegative) 146 | value = -value; 147 | return value; 148 | } 149 | 150 | 151 | // as parseInt but returns a floating point value 152 | float Stream::parseFloat() 153 | { 154 | return parseFloat(NO_SKIP_CHAR); 155 | } 156 | 157 | // as above but the given skipChar is ignored 158 | // this allows format characters (typically commas) in values to be ignored 159 | float Stream::parseFloat(char skipChar){ 160 | bool isNegative = false; 161 | bool isFraction = false; 162 | long value = 0; 163 | char c; 164 | float fraction = 1.0; 165 | 166 | c = peekNextDigit(); 167 | 168 | // ignore non numeric leading characters 169 | if(c < 0) 170 | return 0; // zero returned if timeout 171 | 172 | do{ 173 | if(c == skipChar) 174 | ; // ignore 175 | else if(c == '-') 176 | isNegative = true; 177 | else if (c == '.') 178 | isFraction = true; 179 | else if(c >= '0' && c <= '9') { // is c a digit? 180 | value = value * 10 + c - '0'; 181 | if(isFraction) 182 | fraction *= 0.1; 183 | } 184 | read(); // consume the character we got with peek 185 | c = timedPeek(); 186 | } 187 | while( (c >= '0' && c <= '9') || c == '.' || c == skipChar ); 188 | 189 | if(isNegative) 190 | value = -value; 191 | if(isFraction) 192 | return value * fraction; 193 | else 194 | 195 | return value; 196 | } 197 | 198 | // read characters from stream into buffer 199 | // terminates if length characters have been read, or timeout (see setTimeout) 200 | // returns the number of characters placed in the buffer 201 | // the buffer is NOT null terminated. 202 | // 203 | size_t Stream::readBytes(char *buffer, size_t length) 204 | { 205 | size_t count = 0; 206 | while (count < length) { 207 | int c = timedRead(); 208 | if (c < 0) break; 209 | *buffer++ = (char)c; 210 | count++; 211 | } 212 | return count; 213 | } 214 | 215 | 216 | // as readBytes with terminator character 217 | // terminates if length characters have been read, timeout, or if the terminator character detected 218 | // returns the number of characters placed in the buffer (0 means no valid data found) 219 | 220 | size_t Stream::readBytesUntil(char terminator, char *buffer, size_t length) 221 | { 222 | if (length < 1) return 0; 223 | size_t index = 0; 224 | while (index < length) { 225 | int c = timedRead(); 226 | if (c < 0 || c == terminator) break; 227 | *buffer++ = (char)c; 228 | index++; 229 | } 230 | return index; // return number of characters, not including null terminator 231 | } 232 | 233 | int Stream::findMulti( struct MultiTarget *targets, int tCount) { 234 | // any zero length target string automatically matches and would make 235 | // a mess of the rest of the algorithm. 236 | for (struct MultiTarget *t = targets; t < targets+tCount; ++t) { 237 | if (t->len <= 0) 238 | return t - targets; 239 | } 240 | 241 | while (1) { 242 | int c = timedRead(); 243 | if (c < 0) 244 | return -1; 245 | 246 | for (struct MultiTarget *t = targets; t < targets+tCount; ++t) { 247 | // the simple case is if we match, deal with that first. 248 | if (c == t->str[t->index]) { 249 | if (++t->index == t->len) 250 | return t - targets; 251 | else 252 | continue; 253 | } 254 | 255 | // if not we need to walk back and see if we could have matched further 256 | // down the stream (ie '1112' doesn't match the first position in '11112' 257 | // but it will match the second position so we can't just reset the current 258 | // index to 0 when we find a mismatch. 259 | if (t->index == 0) 260 | continue; 261 | 262 | int origIndex = t->index; 263 | do { 264 | --t->index; 265 | // first check if current char works against the new current index 266 | if (c != t->str[t->index]) 267 | continue; 268 | 269 | // if it's the only char then we're good, nothing more to check 270 | if (t->index == 0) { 271 | t->index++; 272 | break; 273 | } 274 | 275 | // otherwise we need to check the rest of the found string 276 | int diff = origIndex - t->index; 277 | size_t i; 278 | for (i = 0; i < t->index; ++i) { 279 | if (t->str[i] != t->str[i + diff]) 280 | break; 281 | } 282 | 283 | // if we successfully got through the previous loop then our current 284 | // index is good. 285 | if (i == t->index) { 286 | t->index++; 287 | break; 288 | } 289 | 290 | // otherwise we just try the next index 291 | } while (t->index); 292 | } 293 | } 294 | // unreachable 295 | return -1; 296 | } 297 | -------------------------------------------------------------------------------- /hardware/arduino/zuno/libraries/ZUNO_OLED_I2C/ZUNO_OLED_I2C.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | OLED_I2C.cpp - Arduino/chipKit library support for 128x64 pixel SSD1306 OLEDs 3 | Copyright (C)2015 Rinky-Dink Electronics, Henning Karlsen. All right reserved 4 | 5 | This library has been made to make it easy to use 128x64 pixel OLED displays 6 | based on the SSD1306 controller chip with an Arduino or a chipKit. 7 | 8 | You can always find the latest version of the library at 9 | http://www.RinkyDinkElectronics.com/ 10 | 11 | This library is free software; you can redistribute it and/or 12 | modify it under the terms of the CC BY-NC-SA 3.0 license. 13 | Please see the included documents for further information. 14 | 15 | Commercial use of this library requires you to buy a license that 16 | will allow commercial use. This includes using the library, 17 | modified or not, as a tool to sell products. 18 | 19 | The license applies to all part of the library including the 20 | examples and tools supplied with the library. 21 | */ 22 | 23 | #include "ZUNO_OLED_I2C.h" 24 | #include "Wire.h" 25 | 26 | 27 | 28 | #define _sendTWIcommand(D) Wire.beginTransmission(SSD1306_ADDR);\ 29 | Wire.write(SSD1306_COMMAND);\ 30 | Wire.write(D);\ 31 | Wire.endTransmission(); 32 | 33 | OLED::OLED() 34 | { 35 | } 36 | /* 37 | void OLED::sendTWIcommand(byte d) 38 | { 39 | Wire.beginTransmission(SSD1306_ADDR); 40 | Wire.write(SSD1306_COMMAND); 41 | Wire.write(); 42 | Wire.endTransmission(); 43 | }*/ 44 | void OLED::begin() 45 | { 46 | 47 | 48 | Wire.begin(); 49 | 50 | _sendTWIcommand(SSD1306_DISPLAY_OFF); 51 | _sendTWIcommand(SSD1306_SET_DISPLAY_CLOCK_DIV_RATIO); 52 | _sendTWIcommand(0x80); 53 | _sendTWIcommand(SSD1306_SET_MULTIPLEX_RATIO); 54 | _sendTWIcommand(0x3F); 55 | _sendTWIcommand(SSD1306_SET_DISPLAY_OFFSET); 56 | _sendTWIcommand(0x0); 57 | _sendTWIcommand(SSD1306_SET_START_LINE | 0x0); 58 | _sendTWIcommand(SSD1306_CHARGE_PUMP); 59 | _sendTWIcommand(0x14); 60 | _sendTWIcommand(SSD1306_MEMORY_ADDR_MODE); 61 | _sendTWIcommand(0x00); 62 | _sendTWIcommand(SSD1306_SET_SEGMENT_REMAP | 0x1); 63 | _sendTWIcommand(SSD1306_COM_SCAN_DIR_DEC); 64 | _sendTWIcommand(SSD1306_SET_COM_PINS); 65 | _sendTWIcommand(0x12); 66 | _sendTWIcommand(SSD1306_SET_CONTRAST_CONTROL); 67 | _sendTWIcommand(0xCF); 68 | _sendTWIcommand(SSD1306_SET_PRECHARGE_PERIOD); 69 | _sendTWIcommand(0xF1); 70 | _sendTWIcommand(SSD1306_SET_VCOM_DESELECT); 71 | _sendTWIcommand(0x40); 72 | _sendTWIcommand(SSD1306_DISPLAY_ALL_ON_RESUME); 73 | _sendTWIcommand(SSD1306_NORMAL_DISPLAY); 74 | _sendTWIcommand(SSD1306_DISPLAY_ON); 75 | 76 | cx = 0; 77 | cy = 0; 78 | 79 | } 80 | void OLED::clrscr() 81 | { 82 | _sendTWIcommand(SSD1306_SET_COLUMN_ADDR); 83 | _sendTWIcommand(0); 84 | _sendTWIcommand(127); 85 | 86 | _sendTWIcommand(SSD1306_SET_PAGE_ADDR); 87 | _sendTWIcommand(0); 88 | _sendTWIcommand(3); 89 | 90 | 91 | Wire.beginTransmission(SSD1306_ADDR); 92 | Wire.write(SSD1306_DATA_CONTINUE); 93 | word count = 512; 94 | while(count--) 95 | { 96 | Wire.write(0x00); 97 | //if((count % 16) == 0) 98 | // delay(1); 99 | } 100 | Wire.endTransmission(); 101 | delay(5); 102 | 103 | /*_sendTWIcommand(SSD1306_SET_COLUMN_ADDR); 104 | _sendTWIcommand(0); 105 | _sendTWIcommand(127);*/ 106 | 107 | _sendTWIcommand(SSD1306_SET_PAGE_ADDR); 108 | _sendTWIcommand(4); 109 | _sendTWIcommand(7); 110 | 111 | 112 | Wire.beginTransmission(SSD1306_ADDR); 113 | Wire.write(SSD1306_DATA_CONTINUE); 114 | count = 512; 115 | while(count--) 116 | { 117 | Wire.write(0x00); 118 | //if((count % 16) == 0) 119 | // delay(1); 120 | } 121 | Wire.endTransmission(); 122 | _sendTWIcommand(SSD1306_SET_PAGE_ADDR); 123 | _sendTWIcommand(0); 124 | _sendTWIcommand(3); 125 | 126 | 127 | 128 | } 129 | void OLED::writeData(byte * pdata, byte p1, byte p2, byte c1, byte c2) 130 | { 131 | _sendTWIcommand(SSD1306_SET_COLUMN_ADDR); 132 | _sendTWIcommand(c1); 133 | _sendTWIcommand(c2); 134 | 135 | _sendTWIcommand(SSD1306_SET_PAGE_ADDR); 136 | _sendTWIcommand(p1); 137 | _sendTWIcommand(p2); 138 | 139 | Wire.beginTransmission(SSD1306_ADDR); 140 | Wire.write(SSD1306_DATA_CONTINUE); 141 | 142 | word count = (p2 - p1 + 1)*(c2 - c1 + 1); 143 | 144 | while(count--) 145 | { 146 | Wire.write(*pdata); 147 | pdata++; 148 | } 149 | Wire.endTransmission(); 150 | } 151 | //static 152 | byte SmallFont[] = 153 | { 154 | 0x06, 0x08, 0x20, 0x5f, 155 | 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // sp 156 | 0x00, 0x00, 0x00, 0x2f, 0x00, 0x00, // ! 157 | 0x00, 0x00, 0x07, 0x00, 0x07, 0x00, // " 158 | 0x00, 0x14, 0x7f, 0x14, 0x7f, 0x14, // # 159 | 0x00, 0x24, 0x2a, 0x7f, 0x2a, 0x12, // $ 160 | 0x00, 0x23, 0x13, 0x08, 0x64, 0x62, // % 161 | 0x00, 0x36, 0x49, 0x55, 0x22, 0x50, // & 162 | 0x00, 0x00, 0x05, 0x03, 0x00, 0x00, // ' 163 | 0x00, 0x00, 0x1c, 0x22, 0x41, 0x00, // ( 164 | 0x00, 0x00, 0x41, 0x22, 0x1c, 0x00, // ) 165 | 0x00, 0x14, 0x08, 0x3E, 0x08, 0x14, // * 166 | 0x00, 0x08, 0x08, 0x3E, 0x08, 0x08, // + 167 | 0x00, 0x00, 0x00, 0xA0, 0x60, 0x00, // , 168 | 0x00, 0x08, 0x08, 0x08, 0x08, 0x08, // - 169 | 0x00, 0x00, 0x60, 0x60, 0x00, 0x00, // . 170 | 0x00, 0x20, 0x10, 0x08, 0x04, 0x02, // / 171 | 172 | 0x00, 0x3E, 0x51, 0x49, 0x45, 0x3E, // 0 173 | 0x00, 0x00, 0x42, 0x7F, 0x40, 0x00, // 1 174 | 0x00, 0x42, 0x61, 0x51, 0x49, 0x46, // 2 175 | 0x00, 0x21, 0x41, 0x45, 0x4B, 0x31, // 3 176 | 0x00, 0x18, 0x14, 0x12, 0x7F, 0x10, // 4 177 | 0x00, 0x27, 0x45, 0x45, 0x45, 0x39, // 5 178 | 0x00, 0x3C, 0x4A, 0x49, 0x49, 0x30, // 6 179 | 0x00, 0x01, 0x71, 0x09, 0x05, 0x03, // 7 180 | 0x00, 0x36, 0x49, 0x49, 0x49, 0x36, // 8 181 | 0x00, 0x06, 0x49, 0x49, 0x29, 0x1E, // 9 182 | 0x00, 0x00, 0x36, 0x36, 0x00, 0x00, // : 183 | 0x00, 0x00, 0x56, 0x36, 0x00, 0x00, // ; 184 | 0x00, 0x08, 0x14, 0x22, 0x41, 0x00, // < 185 | 0x00, 0x14, 0x14, 0x14, 0x14, 0x14, // = 186 | 0x00, 0x00, 0x41, 0x22, 0x14, 0x08, // > 187 | 0x00, 0x02, 0x01, 0x51, 0x09, 0x06, // ? 188 | 189 | 0x00, 0x32, 0x49, 0x59, 0x51, 0x3E, // @ 190 | 0x00, 0x7C, 0x12, 0x11, 0x12, 0x7C, // A 191 | 0x00, 0x7F, 0x49, 0x49, 0x49, 0x36, // B 192 | 0x00, 0x3E, 0x41, 0x41, 0x41, 0x22, // C 193 | 0x00, 0x7F, 0x41, 0x41, 0x22, 0x1C, // D 194 | 0x00, 0x7F, 0x49, 0x49, 0x49, 0x41, // E 195 | 0x00, 0x7F, 0x09, 0x09, 0x09, 0x01, // F 196 | 0x00, 0x3E, 0x41, 0x49, 0x49, 0x7A, // G 197 | 0x00, 0x7F, 0x08, 0x08, 0x08, 0x7F, // H 198 | 0x00, 0x00, 0x41, 0x7F, 0x41, 0x00, // I 199 | 0x00, 0x20, 0x40, 0x41, 0x3F, 0x01, // J 200 | 0x00, 0x7F, 0x08, 0x14, 0x22, 0x41, // K 201 | 0x00, 0x7F, 0x40, 0x40, 0x40, 0x40, // L 202 | 0x00, 0x7F, 0x02, 0x0C, 0x02, 0x7F, // M 203 | 0x00, 0x7F, 0x04, 0x08, 0x10, 0x7F, // N 204 | 0x00, 0x3E, 0x41, 0x41, 0x41, 0x3E, // O 205 | 206 | 0x00, 0x7F, 0x09, 0x09, 0x09, 0x06, // P 207 | 0x00, 0x3E, 0x41, 0x51, 0x21, 0x5E, // Q 208 | 0x00, 0x7F, 0x09, 0x19, 0x29, 0x46, // R 209 | 0x00, 0x46, 0x49, 0x49, 0x49, 0x31, // S 210 | 0x00, 0x01, 0x01, 0x7F, 0x01, 0x01, // T 211 | 0x00, 0x3F, 0x40, 0x40, 0x40, 0x3F, // U 212 | 0x00, 0x1F, 0x20, 0x40, 0x20, 0x1F, // V 213 | 0x00, 0x3F, 0x40, 0x38, 0x40, 0x3F, // W 214 | 0x00, 0x63, 0x14, 0x08, 0x14, 0x63, // X 215 | 0x00, 0x07, 0x08, 0x70, 0x08, 0x07, // Y 216 | 0x00, 0x61, 0x51, 0x49, 0x45, 0x43, // Z 217 | 0x00, 0x00, 0x7F, 0x41, 0x41, 0x00, // [ 218 | 0xAA, 0x55, 0xAA, 0x55, 0xAA, 0x55, // Backslash (Checker pattern) 219 | 0x00, 0x00, 0x41, 0x41, 0x7F, 0x00, // ] 220 | 0x00, 0x04, 0x02, 0x01, 0x02, 0x04, // ^ 221 | 0x00, 0x40, 0x40, 0x40, 0x40, 0x40, // _ 222 | 223 | 0x00, 0x00, 0x03, 0x05, 0x00, 0x00, // ` 224 | 0x00, 0x20, 0x54, 0x54, 0x54, 0x78, // a 225 | 0x00, 0x7F, 0x48, 0x44, 0x44, 0x38, // b 226 | 0x00, 0x38, 0x44, 0x44, 0x44, 0x20, // c 227 | 0x00, 0x38, 0x44, 0x44, 0x48, 0x7F, // d 228 | 0x00, 0x38, 0x54, 0x54, 0x54, 0x18, // e 229 | 0x00, 0x08, 0x7E, 0x09, 0x01, 0x02, // f 230 | 0x00, 0x18, 0xA4, 0xA4, 0xA4, 0x7C, // g 231 | 0x00, 0x7F, 0x08, 0x04, 0x04, 0x78, // h 232 | 0x00, 0x00, 0x44, 0x7D, 0x40, 0x00, // i 233 | 0x00, 0x40, 0x80, 0x84, 0x7D, 0x00, // j 234 | 0x00, 0x7F, 0x10, 0x28, 0x44, 0x00, // k 235 | 0x00, 0x00, 0x41, 0x7F, 0x40, 0x00, // l 236 | 0x00, 0x7C, 0x04, 0x18, 0x04, 0x78, // m 237 | 0x00, 0x7C, 0x08, 0x04, 0x04, 0x78, // n 238 | 0x00, 0x38, 0x44, 0x44, 0x44, 0x38, // o 239 | 240 | 0x00, 0xFC, 0x24, 0x24, 0x24, 0x18, // p 241 | 0x00, 0x18, 0x24, 0x24, 0x18, 0xFC, // q 242 | 0x00, 0x7C, 0x08, 0x04, 0x04, 0x08, // r 243 | 0x00, 0x48, 0x54, 0x54, 0x54, 0x20, // s 244 | 0x00, 0x04, 0x3F, 0x44, 0x40, 0x20, // t 245 | 0x00, 0x3C, 0x40, 0x40, 0x20, 0x7C, // u 246 | 0x00, 0x1C, 0x20, 0x40, 0x20, 0x1C, // v 247 | 0x00, 0x3C, 0x40, 0x30, 0x40, 0x3C, // w 248 | 0x00, 0x44, 0x28, 0x10, 0x28, 0x44, // x 249 | 0x00, 0x1C, 0xA0, 0xA0, 0xA0, 0x7C, // y 250 | 0x00, 0x44, 0x64, 0x54, 0x4C, 0x44, // z 251 | 0x00, 0x00, 0x10, 0x7C, 0x82, 0x00, // { 252 | 0x00, 0x00, 0x00, 0xFF, 0x00, 0x00, // | 253 | 0x00, 0x00, 0x82, 0x7C, 0x10, 0x00, // } 254 | 0x00, 0x00, 0x06, 0x09, 0x09, 0x06 // ~ (Degrees) 255 | }; 256 | size_t OLED::write(uint8_t value) 257 | { 258 | 259 | 260 | 261 | if(value == '\r') 262 | return 0; 263 | if(value == '\n') 264 | { 265 | cy = (cy + 1)%8; 266 | cx = 0; 267 | return 0; 268 | } 269 | 270 | 271 | { 272 | //writeData(&SmallFont[6*(value - 0x20)+4], cy, cy, cx, cx + 5); 273 | _sendTWIcommand(SSD1306_SET_COLUMN_ADDR); 274 | _sendTWIcommand(cx); 275 | _sendTWIcommand(cx+5); 276 | 277 | _sendTWIcommand(SSD1306_SET_PAGE_ADDR); 278 | _sendTWIcommand(cy); 279 | _sendTWIcommand(cy); 280 | 281 | Wire.beginTransmission(SSD1306_ADDR); 282 | Wire.write(SSD1306_DATA_CONTINUE); 283 | 284 | byte count = 6; 285 | word i = 6*(value - 0x20)+4; 286 | while(count--) 287 | { 288 | Wire.write(SmallFont[i]);//*pdata); 289 | i++; 290 | //pdata++; 291 | } 292 | Wire.endTransmission(); 293 | 294 | cx += 6; 295 | if((cx + 6) > 127) 296 | { 297 | cx = 0; 298 | cy = (cy + 1)%8; 299 | } 300 | } 301 | 302 | return 1; 303 | 304 | 305 | } 306 | void OLED::gotoXY(byte x, byte y) 307 | { 308 | cx = x; 309 | cy = y; 310 | } 311 | void OLED::setBrightness(uint8_t value) 312 | { 313 | _sendTWIcommand(SSD1306_SET_CONTRAST_CONTROL); 314 | _sendTWIcommand(value); 315 | } 316 | 317 | void OLED::invert(bool mode) 318 | { 319 | if (mode) 320 | { 321 | _sendTWIcommand(SSD1306_INVERT_DISPLAY); 322 | } 323 | else 324 | { 325 | _sendTWIcommand(SSD1306_NORMAL_DISPLAY); 326 | } 327 | } 328 | 329 | --------------------------------------------------------------------------------