├── BD7411 ├── BD7411.cpp ├── BD7411.h ├── examples │ └── BD7411 │ │ └── BD7411.ino └── keywords.txt ├── BH1749NUC ├── BH1749NUC.cpp ├── BH1749NUC.h ├── examples │ └── BH1749NUC │ │ └── BH1749NUC.ino └── keywords.txt ├── BM1383AGLV ├── BM1383AGLV.cpp ├── BM1383AGLV.h ├── examples │ └── BM1383AGLV │ │ └── BM1383AGLV.ino └── keywords.txt ├── BM1422AGMV ├── BM1422AGMV.cpp ├── BM1422AGMV.h ├── LICENSE ├── arduinoFFT.cpp ├── arduinoFFT.h ├── examples │ ├── BM1422AGMV │ │ └── BM1422AGMV.ino │ └── BM1422AGMV_FFT_SPRESENSE │ │ └── BM1422AGMV_FFT_SPRESENSE.ino └── keywords.txt ├── KX122 ├── KX122.cpp ├── KX122.h ├── examples │ └── KX122 │ │ └── KX122.ino └── keywords.txt ├── KX126 ├── KX126.cpp ├── KX126.h ├── examples │ └── KX126 │ │ └── KX126.ino └── keywords.txt ├── KX224 ├── KX224.cpp ├── KX224.h ├── examples │ └── KX224 │ │ └── KX224.ino └── keywords.txt ├── LICENSE ├── MK71251-02 ├── MK71251.cpp ├── MK71251.h ├── examples │ └── MK71251-02 │ │ └── MK71251-02.ino └── keywords.txt ├── README.md ├── RPR-0521RS ├── RPR-0521RS.cpp ├── RPR-0521RS.h ├── examples │ └── RPR-0521RS │ │ └── RPR-0521RS.ino └── keywords.txt ├── SPRESENSE-Add-on-board ├── BOM_BLE_Add-on.xlsx ├── BOM_Sensor_Add-on.xlsx ├── SPRESENSE_BLE_add-on_Board.pdf └── SPRESENSE_Sensor_add-on_Board.pdf ├── SPRESENSE-WISUN-EVK-701 ├── bp35c0-j11.cpp ├── bp35c0-j11.h ├── documents │ ├── BP35C0-J11(Wi-SUN Enhanced HAN) │ │ └── J11_UART_IFコマンド仕様書_第1.1版.pdf │ ├── BP35C2(USB dongle) │ │ └── BP35C0_BP35C2-command_reference-dse-j.pdf │ └── SPRESENSE-WiSUN-EVK-701_サンプルソフトウェア説明書_ROHC.pdf ├── examples │ └── SPRESENSE-WISUN-EVK-701 │ │ └── SPRESENSE-WISUN-EVK-701.ino └── keywords.txt ├── Sensors-Add-on-Demo └── Sensors-Add-on-Demo.ino ├── images ├── add_library.PNG ├── arduino_ide.png ├── ble_pins2.jpg ├── sens_pins2.jpg ├── serial_monitor.png └── sketch_folder.png └── kx13x ├── examples └── KX13X │ └── kx13x.ino ├── keywords.txt ├── kx132_1211_registers.h ├── kx134_1211_registers.h ├── kx13x.c ├── kx13x.h ├── kx13x_example.c ├── kx13x_example.h └── platform.h /BD7411/BD7411.cpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | BD7411.cpp 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | //#include 25 | #include 26 | #include "BD7411.h" 27 | 28 | BD7411::BD7411(void) 29 | { 30 | 31 | } 32 | 33 | void BD7411::init(int pin) 34 | { 35 | _out_pin = pin; 36 | } 37 | 38 | int BD7411::readoutpin(void) 39 | { 40 | int rc; 41 | 42 | rc = digitalRead(_out_pin); 43 | return (rc); 44 | } 45 | -------------------------------------------------------------------------------- /BD7411/BD7411.h: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | BD7411.h 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #ifndef _BD7411_H_ 25 | #define _BD7411_H_ 26 | 27 | class BD7411 28 | { 29 | public: 30 | BD7411(); 31 | void init(int pin); 32 | int readoutpin(void); 33 | private: 34 | int _out_pin; 35 | }; 36 | 37 | #endif // _BD7411_H_ 38 | -------------------------------------------------------------------------------- /BD7411/examples/BD7411/BD7411.ino: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | BD7411.ino 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #include "BD7411.h" 25 | #include 26 | 27 | int hallout_pin = 0; // use D0 pin (extension board) 28 | 29 | BD7411 bd7411; 30 | 31 | void setup() { 32 | 33 | Serial.begin(115200); 34 | while (!Serial); 35 | 36 | bd7411.init(hallout_pin); 37 | 38 | Serial.println("BD7411G Sample"); 39 | } 40 | 41 | void loop() { 42 | 43 | int hallout; 44 | 45 | hallout = bd7411.readoutpin(); 46 | if (hallout == 0) { 47 | Serial.println("BD7411G Magnet field Detect!"); 48 | } else { 49 | Serial.println(); 50 | } 51 | 52 | delay(500); 53 | } 54 | 55 | -------------------------------------------------------------------------------- /BD7411/keywords.txt: -------------------------------------------------------------------------------- 1 | BD7411 KEYWORD1 2 | init KEYWORD2 3 | readoutpin KEYWORD2 4 | -------------------------------------------------------------------------------- /BH1749NUC/BH1749NUC.cpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | BH1749NUC.cpp 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | //#include 25 | #include 26 | #include 27 | #include "BH1749NUC.h" 28 | 29 | BH1749NUC::BH1749NUC(int slave_address) 30 | { 31 | _device_address = slave_address; 32 | } 33 | 34 | BH1749NUC::~BH1749NUC() 35 | { 36 | _device_address = 0; 37 | } 38 | 39 | byte BH1749NUC::init(void) 40 | { 41 | byte rc; 42 | unsigned char reg; 43 | 44 | rc = read(BH1749NUC_SYSTEM_CONTROL, ®, sizeof(reg)); 45 | if (rc != 0) { 46 | Serial.println("Can't access BH1749NUC"); 47 | return (rc); 48 | } 49 | reg = reg & 0x3F; 50 | Serial.print("BH1749NUC Part ID Value = "); 51 | Serial.println(reg, HEX); 52 | 53 | if (reg != BH1749NUC_PART_ID_VAL) { 54 | Serial.println("Can't find BH1749NUC"); 55 | return (rc); 56 | } 57 | 58 | rc = read(BH1749NUC_MANUFACTURER_ID, ®, sizeof(reg)); 59 | if (rc != 0) { 60 | Serial.println("Can't access BH1749NUC"); 61 | return (rc); 62 | } 63 | Serial.print("BH1749NUC MANUFACTURER ID Register Value = "); 64 | Serial.println(reg, HEX); 65 | 66 | if (reg != BH1749NUC_MANUFACT_ID_VAL) { 67 | Serial.println("Can't find BH1749NUC"); 68 | return (rc); 69 | } 70 | 71 | reg = BH1749NUC_MODE_CONTROL1_VAL; 72 | rc = write(BH1749NUC_MODE_CONTROL1, ®, sizeof(reg)); 73 | if (rc != 0) { 74 | Serial.println("Can't write BH1749NUC MODE_CONTROL1 register"); 75 | return (rc); 76 | } 77 | 78 | reg = BH1749NUC_MODE_CONTROL2_VAL; 79 | rc = write(BH1749NUC_MODE_CONTROL2, ®, sizeof(reg)); 80 | if (rc != 0) { 81 | Serial.println("Can't write BH1749NUC MODE_CONTROL2 register"); 82 | return (rc); 83 | } 84 | 85 | delay(WAIT_TMT2_MAX); 86 | 87 | return (rc); 88 | } 89 | 90 | byte BH1749NUC::get_rawval(unsigned char *data) 91 | { 92 | byte rc; 93 | 94 | rc = read(BH1749NUC_RED_DATA_LSB, data, GET_BYTE_RED_TO_GREEN2); 95 | if (rc != 0) { 96 | Serial.println("Can't get BH1749NUC RGB, IR and GREEN2 value"); 97 | } 98 | 99 | return (rc); 100 | } 101 | 102 | byte BH1749NUC::get_val(unsigned short *data) 103 | { 104 | byte rc; 105 | unsigned char val[GET_BYTE_RED_TO_GREEN2]; 106 | 107 | rc = get_rawval(val); 108 | if (rc != 0) { 109 | return (rc); 110 | } 111 | 112 | //val[6] and val[7] are RESERVED Register Value 113 | data[0] = ((unsigned short)val[1] << 8) | val[0]; 114 | data[1] = ((unsigned short)val[3] << 8) | val[2]; 115 | data[2] = ((unsigned short)val[5] << 8) | val[4]; 116 | data[3] = ((unsigned short)val[9] << 8) | val[8]; 117 | data[4] = ((unsigned short)val[11] << 8) | val[10]; 118 | 119 | return (rc); 120 | } 121 | 122 | byte BH1749NUC::write(unsigned char memory_address, unsigned char *data, unsigned char size) 123 | { 124 | byte rc; 125 | 126 | Wire.beginTransmission(_device_address); 127 | Wire.write(memory_address); 128 | Wire.write(data, size); 129 | rc = Wire.endTransmission(); 130 | return (rc); 131 | } 132 | 133 | byte BH1749NUC::read(unsigned char memory_address, unsigned char *data, int size) 134 | { 135 | byte rc; 136 | unsigned char cnt; 137 | 138 | Wire.beginTransmission(_device_address); 139 | Wire.write(memory_address); 140 | rc = Wire.endTransmission(false); 141 | if (rc != 0) { 142 | return (rc); 143 | } 144 | 145 | Wire.requestFrom(_device_address, size, true); 146 | cnt = 0; 147 | while(Wire.available()) { 148 | data[cnt] = Wire.read(); 149 | cnt++; 150 | } 151 | 152 | return (0); 153 | } 154 | -------------------------------------------------------------------------------- /BH1749NUC/BH1749NUC.h: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | BH1749NUC.h 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #ifndef _BH1749NUC_H_ 25 | #define _BH1749NUC_H_ 26 | 27 | #define BH1749NUC_DEVICE_ADDRESS_38 (0x38) // 7bit Addrss 28 | #define BH1749NUC_DEVICE_ADDRESS_39 (0x39) // 7bit Addrss 29 | #define BH1749NUC_PART_ID_VAL (0x0D) 30 | #define BH1749NUC_MANUFACT_ID_VAL (0xE0) 31 | 32 | #define BH1749NUC_SYSTEM_CONTROL (0x40) 33 | #define BH1749NUC_MODE_CONTROL1 (0x41) 34 | #define BH1749NUC_MODE_CONTROL2 (0x42) 35 | #define BH1749NUC_RED_DATA_LSB (0x50) 36 | #define BH1749NUC_MANUFACTURER_ID (0x92) 37 | 38 | #define BH1749NUC_MODE_CONTROL1_MEAS_MODE_120MS (2) 39 | #define BH1749NUC_MODE_CONTROL1_MEAS_MODE_240MS (3) 40 | #define BH1749NUC_MODE_CONTROL1_RGB_GAIN_X1 (1 << 3) 41 | #define BH1749NUC_MODE_CONTROL1_RGB_GAIN_X32 (3 << 3) 42 | #define BH1749NUC_MODE_CONTROL1_IR_GAIN_X1 (1 << 5) 43 | #define BH1749NUC_MODE_CONTROL1_IR_GAIN_X32 (3 << 5) 44 | #define BH1749NUC_MODE_CONTROL2_RGB_EN (1 << 4) 45 | 46 | #define BH1749NUC_MODE_CONTROL1_VAL (BH1749NUC_MODE_CONTROL1_MEAS_MODE_120MS | BH1749NUC_MODE_CONTROL1_RGB_GAIN_X1 | BH1749NUC_MODE_CONTROL1_IR_GAIN_X1) 47 | #define BH1749NUC_MODE_CONTROL2_VAL (BH1749NUC_MODE_CONTROL2_RGB_EN) 48 | 49 | #define GET_BYTE_RED_TO_GREEN2 (12) 50 | #define WAIT_TMT2_MAX (340) 51 | 52 | class BH1749NUC 53 | { 54 | public: 55 | BH1749NUC(int slave_address); 56 | ~BH1749NUC(); 57 | byte init(void) ; 58 | byte get_rawval(unsigned char *data); 59 | byte get_val(unsigned short *data); 60 | byte write(unsigned char memory_address, unsigned char *data, unsigned char size); 61 | byte read(unsigned char memory_address, unsigned char *data, int size); 62 | private: 63 | int _device_address; 64 | }; 65 | 66 | #endif // _BH1749NUC_H_ 67 | -------------------------------------------------------------------------------- /BH1749NUC/examples/BH1749NUC/BH1749NUC.ino: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | BH1749NUC.ino 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #include 25 | #include "BH1749NUC.h" 26 | 27 | BH1749NUC bh1749nuc(BH1749NUC_DEVICE_ADDRESS_39); 28 | 29 | void setup() { 30 | byte rc; 31 | 32 | Serial.begin(115200); 33 | while (!Serial); 34 | 35 | Wire.begin(); 36 | 37 | rc = bh1749nuc.init(); 38 | if (rc != 0) { 39 | Serial.println("BH1749NUC initialization failed"); 40 | Serial.flush(); 41 | } 42 | } 43 | 44 | void loop() { 45 | byte rc; 46 | unsigned short color[5]; 47 | 48 | rc = bh1749nuc.get_val(color); 49 | if (rc == 0) { 50 | Serial.write("BH1749NUC (RED) = "); 51 | Serial.println(color[0]); 52 | Serial.write("BH1749NUC (GREEN) = "); 53 | Serial.println(color[1]); 54 | Serial.write("BH1749NUC (BLUE) = "); 55 | Serial.println(color[2]); 56 | Serial.write("BH1749NUC (IR) = "); 57 | Serial.println(color[3]); 58 | Serial.write("BH1749NUC (GREEN2) = "); 59 | Serial.println(color[4]); 60 | Serial.println(); 61 | } 62 | 63 | delay(WAIT_TMT2_MAX); 64 | 65 | } 66 | -------------------------------------------------------------------------------- /BH1749NUC/keywords.txt: -------------------------------------------------------------------------------- 1 | BH1749NUC KEYWORD1 2 | init KEYWORD2 3 | get_rawval KEYWORD2 4 | get_val KEYWORD2 5 | write KEYWORD2 6 | read KEYWORD2 7 | -------------------------------------------------------------------------------- /BM1383AGLV/BM1383AGLV.cpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | BM1383AGLV.cpp 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #include 25 | #include "Arduino.h" 26 | #include "BM1383AGLV.h" 27 | 28 | BM1383AGLV::BM1383AGLV(void) 29 | { 30 | 31 | } 32 | 33 | byte BM1383AGLV::init(void) 34 | { 35 | byte rc; 36 | unsigned char reg; 37 | 38 | rc = read(BM1383AGLV_ID, ®, sizeof(reg)); 39 | if (rc != 0) { 40 | Serial.println("Can't access BM1383AGLV"); 41 | return (rc); 42 | } 43 | Serial.print("BM1383GL ID Register Value = 0x"); 44 | Serial.println(reg, HEX); 45 | 46 | if (reg != BM1383AGLV_ID_VAL) { 47 | Serial.println("Can't find BM1383AGLV"); 48 | return (rc); 49 | } 50 | 51 | reg = BM1383AGLV_POWER_DOWN_VAL; 52 | rc = write(BM1383AGLV_POWER_DOWN, ®, sizeof(reg)); 53 | if (rc != 0) { 54 | Serial.println("Can't write BM1383AGLV POWER_DOWN register"); 55 | return (rc); 56 | } 57 | 58 | delay(WAIT_BETWEEN_POWER_DOWN_AND_RESET); 59 | 60 | reg = BM1383AGLV_RESET_VAL; 61 | rc = write(BM1383AGLV_RESET, ®, sizeof(reg)); 62 | if (rc != 0) { 63 | Serial.println("Can't write BM1383AGLV SLEEP register"); 64 | return (rc); 65 | } 66 | 67 | reg = BM1383AGLV_MODE_CONTROL_VAL; 68 | rc = write(BM1383AGLV_MODE_CONTROL, ®, sizeof(reg)); 69 | if (rc != 0) { 70 | Serial.println("Can't write BM1383AGLV MODE_CONTROL register"); 71 | return (rc); 72 | } 73 | 74 | delay(WAIT_TMT_MAX); 75 | 76 | return (rc); 77 | 78 | } 79 | 80 | byte BM1383AGLV::get_rawval(unsigned char *data) 81 | { 82 | byte rc; 83 | 84 | rc = read(BM1383AGLV_PRESSURE_MSB, data, GET_BYTE_PRESS_TEMP); 85 | if (rc != 0) { 86 | Serial.println("Can't get BM1383AGLV PRESS value"); 87 | } 88 | 89 | return (rc); 90 | } 91 | 92 | byte BM1383AGLV::get_val( float *press, float *temp) 93 | { 94 | byte rc; 95 | unsigned char val[GET_BYTE_PRESS_TEMP]; 96 | unsigned long rawpress; 97 | short rawtemp; 98 | 99 | rc = get_rawval(val); 100 | if (rc != 0) { 101 | return (rc); 102 | } 103 | 104 | rawpress = (((unsigned long)val[0] << 16) | ((unsigned long)val[1] << 8) | val[2]&0xFC) >> 2; 105 | 106 | if (rawpress == 0) { 107 | return (-1); 108 | } 109 | 110 | *press = (float)rawpress / HPA_PER_COUNT; 111 | 112 | rawtemp = ((short)val[3] << 8) | val[4]; 113 | 114 | if (rawtemp == 0) { 115 | return (-1); 116 | } 117 | 118 | *temp = (float)rawtemp / DEGREES_CELSIUS_PER_COUNT; 119 | 120 | return (rc); 121 | } 122 | 123 | byte BM1383AGLV::write(unsigned char memory_address, unsigned char *data, unsigned char size) 124 | { 125 | byte rc; 126 | unsigned int cnt; 127 | 128 | Wire.beginTransmission(BM1383AGLV_DEVICE_ADDRESS); 129 | Wire.write(memory_address); 130 | Wire.write(data, size); 131 | rc = Wire.endTransmission(); 132 | return (rc); 133 | } 134 | 135 | byte BM1383AGLV::read(unsigned char memory_address, unsigned char *data, int size) 136 | { 137 | byte rc; 138 | unsigned char cnt; 139 | 140 | Wire.beginTransmission(BM1383AGLV_DEVICE_ADDRESS); 141 | Wire.write(memory_address); 142 | rc = Wire.endTransmission(false); 143 | if (rc != 0) { 144 | return (rc); 145 | } 146 | 147 | Wire.requestFrom((int)BM1383AGLV_DEVICE_ADDRESS, (int)size, (int)true); 148 | cnt = 0; 149 | while(Wire.available()) { 150 | data[cnt] = Wire.read(); 151 | cnt++; 152 | } 153 | 154 | return (rc); 155 | } 156 | -------------------------------------------------------------------------------- /BM1383AGLV/BM1383AGLV.h: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | BM1383AGLV.h 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #ifndef _BM1383AGLV_H_ 25 | #define _BM1383AGLV_H_ 26 | 27 | #define BM1383AGLV_DEVICE_ADDRESS (0x5D) // 7bit Addrss 28 | #define BM1383AGLV_ID_VAL (0x32) 29 | 30 | #define BM1383AGLV_ID (0x10) 31 | #define BM1383AGLV_POWER_DOWN (0x12) 32 | #define BM1383AGLV_RESET (0x13) 33 | #define BM1383AGLV_MODE_CONTROL (0x14) 34 | #define BM1383AGLV_PRESSURE_MSB (0x1A) 35 | 36 | #define BM1383AGLV_POWER_DOWN_PWR_DOWN (1 << 0) 37 | #define BM1383AGLV_RESET_RSTB (1 << 0) 38 | #define BM1383AGLV_MODE_CONTROL_AVE_NUM64 (6 << 5) 39 | #define BM1383AGLV_MODE_CONTROL_RESERVED_3BIT (1 << 3) 40 | #define BM1383AGLV_MODE_CONTROL_MODE_CONTINUOUS (4 << 0) 41 | 42 | #define BM1383AGLV_POWER_DOWN_VAL (BM1383AGLV_POWER_DOWN_PWR_DOWN) 43 | #define BM1383AGLV_RESET_VAL (BM1383AGLV_RESET_RSTB) 44 | #define BM1383AGLV_MODE_CONTROL_VAL (BM1383AGLV_MODE_CONTROL_AVE_NUM64 | BM1383AGLV_MODE_CONTROL_RESERVED_3BIT | BM1383AGLV_MODE_CONTROL_MODE_CONTINUOUS) 45 | 46 | #define HPA_PER_COUNT (2048) 47 | #define DEGREES_CELSIUS_PER_COUNT (32) 48 | #define GET_BYTE_PRESS_TEMP (5) 49 | #define WAIT_TMT_MAX (240) 50 | #define WAIT_BETWEEN_POWER_DOWN_AND_RESET (2) 51 | 52 | class BM1383AGLV 53 | { 54 | public: 55 | BM1383AGLV(void); 56 | byte init(void) ; 57 | byte get_rawval(unsigned char *data); 58 | byte get_val(float *press, float *temp); 59 | byte write(unsigned char memory_address, unsigned char *data, unsigned char size); 60 | byte read(unsigned char memory_address, unsigned char *data, int size); 61 | }; 62 | 63 | #endif // _BM1383AGLV_H_ 64 | -------------------------------------------------------------------------------- /BM1383AGLV/examples/BM1383AGLV/BM1383AGLV.ino: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | BM1383AGLV.ino 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #include 25 | #include "BM1383AGLV.h" 26 | 27 | BM1383AGLV bm1383aglv; 28 | 29 | void setup() { 30 | byte rc; 31 | 32 | Serial.begin(115200); 33 | while (!Serial); 34 | 35 | Wire.begin(); 36 | 37 | rc = bm1383aglv.init(); 38 | if (rc != 0) { 39 | Serial.println("BM1383AGLV initialization failed"); 40 | Serial.flush(); 41 | } 42 | } 43 | 44 | void loop() { 45 | byte rc; 46 | float press = 0, temp = 0; 47 | 48 | rc = bm1383aglv.get_val(&press, &temp); 49 | if (rc == 0) { 50 | Serial.print("BM1383AGLV (PRESS) = "); 51 | Serial.print(press); 52 | Serial.println(" [hPa]"); 53 | Serial.print("BM1383AGLV (TEMP) = "); 54 | Serial.print(temp); 55 | Serial.println(" [degrees Celsius]"); 56 | Serial.println(); 57 | } 58 | 59 | delay(500); 60 | 61 | } 62 | 63 | -------------------------------------------------------------------------------- /BM1383AGLV/keywords.txt: -------------------------------------------------------------------------------- 1 | BM1383AGLV KEYWORD1 2 | init KEYWORD2 3 | get_rawval KEYWORD2 4 | get_val KEYWORD2 5 | write KEYWORD2 6 | read KEYWORD2 7 | -------------------------------------------------------------------------------- /BM1422AGMV/BM1422AGMV.cpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | BM1422AGMV.cpp 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #include 25 | #include "Arduino.h" 26 | #include "BM1422AGMV.h" 27 | 28 | BM1422AGMV::BM1422AGMV(int slave_address) 29 | { 30 | _device_address = slave_address ; 31 | } 32 | 33 | byte BM1422AGMV::init(void) 34 | { 35 | byte rc; 36 | unsigned char reg; 37 | unsigned char buf[2]; 38 | 39 | rc = read(BM1422AGMV_WIA, ®, sizeof(reg)); 40 | if (rc != 0) { 41 | Serial.println("Can't access BM1422AGMV"); 42 | return (rc); 43 | } 44 | Serial.print("BM1422AGMV_WHO_AMI Register Value = 0x"); 45 | Serial.println(reg, HEX); 46 | 47 | if (reg != BM1422AGMV_WIA_VAL) { 48 | Serial.println("Can't find BM1422AGMV"); 49 | return (rc); 50 | } 51 | 52 | // Step1 53 | reg = BM1422AGMV_CNTL1_VAL; 54 | rc = write(BM1422AGMV_CNTL1, ®, sizeof(reg)); 55 | if (rc != 0) { 56 | Serial.println("Can't write BM1422AGMV_CNTL1 Register"); 57 | return (rc); 58 | } 59 | 60 | // Check 12bit or 14bit 61 | buf[0] = (BM1422AGMV_CNTL1_VAL & BM1422AGMV_CNTL1_OUT_BIT); 62 | if (buf[0] == BM1422AGMV_CNTL1_OUT_BIT) { 63 | _sens = BM1422AGMV_14BIT_SENS; 64 | } else { 65 | _sens = BM1422AGMV_12BIT_SENS; 66 | } 67 | 68 | delay(1); 69 | 70 | buf[0] = (BM1422AGMV_CNTL4_VAL >> 8) & 0xFF; 71 | buf[1] = (BM1422AGMV_CNTL4_VAL & 0xFF); 72 | rc = write(BM1422AGMV_CNTL4, buf, sizeof(buf)); 73 | if (rc != 0) { 74 | Serial.println("Can't write BM1422AGMV_CNTL4 Register"); 75 | return (rc); 76 | } 77 | 78 | // Step2 79 | reg = BM1422AGMV_CNTL2_VAL; 80 | rc = write(BM1422AGMV_CNTL2, ®, sizeof(reg)); 81 | if (rc != 0) { 82 | Serial.println("Can't write BM1422AGMV_CNTL2 Register"); 83 | return (rc); 84 | } 85 | 86 | // Step3 87 | 88 | // Option 89 | reg = BM1422AGMV_AVE_A_VAL; 90 | rc = write(BM1422AGMV_AVE_A, ®, sizeof(reg)); 91 | if (rc != 0) { 92 | Serial.println("Can't write BM1422AGMV_AVE_A Register"); 93 | return (rc); 94 | } 95 | 96 | return (rc); 97 | } 98 | 99 | byte BM1422AGMV::get_rawval(unsigned char *data) 100 | { 101 | byte rc; 102 | unsigned char reg; 103 | 104 | // Step4 105 | reg = BM1422AGMV_CNTL3_VAL; 106 | rc = write(BM1422AGMV_CNTL3, ®, sizeof(reg)); 107 | if (rc != 0) { 108 | Serial.println("Can't write BM1422AGMV_CNTL3 Register"); 109 | return (rc); 110 | } 111 | 112 | delay(2); 113 | 114 | rc = read(BM1422AGMV_DATAX, data, 6); 115 | if (rc != 0) { 116 | Serial.println("Can't get BM1422AGMV magnet values"); 117 | } 118 | 119 | return (rc); 120 | } 121 | 122 | byte BM1422AGMV::get_val(float *data) 123 | { 124 | byte rc; 125 | unsigned char val[6]; 126 | signed short mag[3]; 127 | 128 | rc = get_rawval(val); 129 | if (rc != 0) { 130 | return (rc); 131 | } 132 | 133 | mag[0] = ((signed short)val[1] << 8) | (val[0]); 134 | mag[1] = ((signed short)val[3] << 8) | (val[2]); 135 | mag[2] = ((signed short)val[5] << 8) | (val[4]); 136 | 137 | convert_uT(mag, data); 138 | 139 | return (rc); 140 | } 141 | 142 | void BM1422AGMV::convert_uT(signed short *rawdata, float *data) 143 | { 144 | // LSB to uT 145 | data[0] = (float)rawdata[0] / _sens; 146 | data[1] = (float)rawdata[1] / _sens; 147 | data[2] = (float)rawdata[2] / _sens; 148 | } 149 | 150 | byte BM1422AGMV::write(unsigned char memory_address, unsigned char *data, unsigned char size) 151 | { 152 | byte rc; 153 | unsigned int cnt; 154 | 155 | Wire.beginTransmission(_device_address); 156 | Wire.write(memory_address); 157 | Wire.write(data, size); 158 | rc = Wire.endTransmission(); 159 | return (rc); 160 | } 161 | 162 | byte BM1422AGMV::read(unsigned char memory_address, unsigned char *data, int size) 163 | { 164 | byte rc; 165 | unsigned char cnt; 166 | 167 | Wire.beginTransmission(_device_address); 168 | Wire.write(memory_address); 169 | rc = Wire.endTransmission(false); 170 | if (rc != 0) { 171 | return (rc); 172 | } 173 | 174 | Wire.requestFrom((int)_device_address, (int)size, (int)true); 175 | cnt = 0; 176 | while(Wire.available()) { 177 | data[cnt] = Wire.read(); 178 | cnt++; 179 | } 180 | 181 | return (rc); 182 | } 183 | -------------------------------------------------------------------------------- /BM1422AGMV/BM1422AGMV.h: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | BM1422AGMV.h 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #ifndef _BM1422AGMV_H_ 25 | #define _BM1422AGMV_H_ 26 | 27 | #define BM1422AGMV_DEVICE_ADDRESS_0E (0x0E) // 7bit Addrss 28 | #define BM1422AGMV_DEVICE_ADDRESS_0F (0x0F) // 7bit Address 29 | #define BM1422AGMV_WIA_VAL (0x41) 30 | 31 | #define BM1422AGMV_WIA (0x0F) 32 | #define BM1422AGMV_DATAX (0x10) 33 | #define BM1422AGMV_STA1 (0x18) 34 | #define BM1422AGMV_CNTL1 (0x1B) 35 | #define BM1422AGMV_CNTL2 (0x1C) 36 | #define BM1422AGMV_CNTL3 (0x1D) 37 | #define BM1422AGMV_AVE_A (0x40) 38 | #define BM1422AGMV_CNTL4 (0x5C) 39 | 40 | #define BM1422AGMV_STA1_RD_DRDY (1 << 6) 41 | 42 | #define BM1422AGMV_CNTL1_FS1 (1 << 1) 43 | #define BM1422AGMV_CNTL1_ODR_10Hz (0 << 3) 44 | #define BM1422AGMV_CNTL1_RST_LV (1 << 5) 45 | #define BM1422AGMV_CNTL1_OUT_BIT (1 << 6) 46 | #define BM1422AGMV_CNTL1_PC1 (1 << 7) 47 | 48 | #define BM1422AGMV_CNTL2_DRP (1 << 2) 49 | #define BM1422AGMV_CNTL2_DREN (1 << 3) 50 | 51 | #define BM1422AGMV_CNTL3_FORCE (1 << 6) 52 | 53 | #define BM1422AGMV_AVE_A_AVE4 (0 << 2) 54 | 55 | #define BM1422AGMV_CNTL1_VAL (BM1422AGMV_CNTL1_FS1 | BM1422AGMV_CNTL1_OUT_BIT | BM1422AGMV_CNTL1_PC1) 56 | #define BM1422AGMV_CNTL2_VAL (BM1422AGMV_CNTL2_DREN) 57 | #define BM1422AGMV_CNTL3_VAL (BM1422AGMV_CNTL3_FORCE) 58 | #define BM1422AGMV_CNTL4_VAL (0x0000) 59 | #define BM1422AGMV_AVE_A_VAL (BM1422AGMV_AVE_A_AVE4) 60 | 61 | #define BM1422AGMV_14BIT_SENS (24) 62 | #define BM1422AGMV_12BIT_SENS (6) 63 | 64 | class BM1422AGMV 65 | { 66 | public: 67 | BM1422AGMV(int slave_address); 68 | byte init(void) ; 69 | byte get_rawval(unsigned char *data); 70 | byte get_val(float *data); 71 | void convert_uT(signed short *rawdata, float *data); 72 | byte write(unsigned char memory_address, unsigned char *data, unsigned char size); 73 | byte read(unsigned char memory_address, unsigned char *data, int size); 74 | private: 75 | int _device_address; 76 | unsigned char _sens; 77 | }; 78 | 79 | #endif // _BM1422AGMV_H_ 80 | -------------------------------------------------------------------------------- /BM1422AGMV/arduinoFFT.cpp: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | FFT libray 4 | Copyright (C) 2010 Didier Longueville 5 | Copyright (C) 2014 Enrique Condes 6 | 7 | This program is free software: you can redistribute it and/or modify 8 | it under the terms of the GNU General Public License as published by 9 | the Free Software Foundation, either version 3 of the License, or 10 | (at your option) any later version. 11 | 12 | This program 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 program. If not, see . 19 | 20 | */ 21 | 22 | #include "arduinoFFT.h" 23 | 24 | arduinoFFT::arduinoFFT(void) 25 | { // Constructor 26 | #warning("This method is deprecated and may be removed on future revisions.") 27 | } 28 | 29 | arduinoFFT::arduinoFFT(double *vReal, double *vImag, uint16_t samples, double samplingFrequency) 30 | {// Constructor 31 | this->_vReal = vReal; 32 | this->_vImag = vImag; 33 | this->_samples = samples; 34 | this->_samplingFrequency = samplingFrequency; 35 | this->_power = Exponent(samples); 36 | } 37 | 38 | arduinoFFT::~arduinoFFT(void) 39 | { 40 | // Destructor 41 | } 42 | 43 | uint8_t arduinoFFT::Revision(void) 44 | { 45 | return(FFT_LIB_REV); 46 | } 47 | 48 | void arduinoFFT::Compute(double *vReal, double *vImag, uint16_t samples, uint8_t dir) 49 | { 50 | #warning("This method is deprecated and may be removed on future revisions.") 51 | Compute(vReal, vImag, samples, Exponent(samples), dir); 52 | } 53 | 54 | void arduinoFFT::Compute(uint8_t dir) 55 | {// Computes in-place complex-to-complex FFT / 56 | // Reverse bits / 57 | uint16_t j = 0; 58 | for (uint16_t i = 0; i < (this->_samples - 1); i++) { 59 | if (i < j) { 60 | Swap(&this->_vReal[i], &this->_vReal[j]); 61 | if(dir==FFT_REVERSE) 62 | Swap(&this->_vImag[i], &this->_vImag[j]); 63 | } 64 | uint16_t k = (this->_samples >> 1); 65 | while (k <= j) { 66 | j -= k; 67 | k >>= 1; 68 | } 69 | j += k; 70 | } 71 | // Compute the FFT / 72 | #ifdef __AVR__ 73 | uint8_t index = 0; 74 | #endif 75 | double c1 = -1.0; 76 | double c2 = 0.0; 77 | uint16_t l2 = 1; 78 | for (uint8_t l = 0; (l < this->_power); l++) { 79 | uint16_t l1 = l2; 80 | l2 <<= 1; 81 | double u1 = 1.0; 82 | double u2 = 0.0; 83 | for (j = 0; j < l1; j++) { 84 | for (uint16_t i = j; i < this->_samples; i += l2) { 85 | uint16_t i1 = i + l1; 86 | double t1 = u1 * this->_vReal[i1] - u2 * this->_vImag[i1]; 87 | double t2 = u1 * this->_vImag[i1] + u2 * this->_vReal[i1]; 88 | this->_vReal[i1] = this->_vReal[i] - t1; 89 | this->_vImag[i1] = this->_vImag[i] - t2; 90 | this->_vReal[i] += t1; 91 | this->_vImag[i] += t2; 92 | } 93 | double z = ((u1 * c1) - (u2 * c2)); 94 | u2 = ((u1 * c2) + (u2 * c1)); 95 | u1 = z; 96 | } 97 | #ifdef __AVR__ 98 | c2 = pgm_read_float_near(&(_c2[index])); 99 | c1 = pgm_read_float_near(&(_c1[index])); 100 | index++; 101 | #else 102 | c2 = sqrt((1.0 - c1) / 2.0); 103 | c1 = sqrt((1.0 + c1) / 2.0); 104 | #endif 105 | if (dir == FFT_FORWARD) { 106 | c2 = -c2; 107 | } 108 | } 109 | // Scaling for reverse transform / 110 | if (dir != FFT_FORWARD) { 111 | for (uint16_t i = 0; i < this->_samples; i++) { 112 | this->_vReal[i] /= this->_samples; 113 | this->_vImag[i] /= this->_samples; 114 | } 115 | } 116 | } 117 | 118 | void arduinoFFT::Compute(double *vReal, double *vImag, uint16_t samples, uint8_t power, uint8_t dir) 119 | { // Computes in-place complex-to-complex FFT 120 | // Reverse bits 121 | #warning("This method is deprecated and may be removed on future revisions.") 122 | uint16_t j = 0; 123 | for (uint16_t i = 0; i < (samples - 1); i++) { 124 | if (i < j) { 125 | Swap(&vReal[i], &vReal[j]); 126 | if(dir==FFT_REVERSE) 127 | Swap(&vImag[i], &vImag[j]); 128 | } 129 | uint16_t k = (samples >> 1); 130 | while (k <= j) { 131 | j -= k; 132 | k >>= 1; 133 | } 134 | j += k; 135 | } 136 | // Compute the FFT 137 | #ifdef __AVR__ 138 | uint8_t index = 0; 139 | #endif 140 | double c1 = -1.0; 141 | double c2 = 0.0; 142 | uint16_t l2 = 1; 143 | for (uint8_t l = 0; (l < power); l++) { 144 | uint16_t l1 = l2; 145 | l2 <<= 1; 146 | double u1 = 1.0; 147 | double u2 = 0.0; 148 | for (j = 0; j < l1; j++) { 149 | for (uint16_t i = j; i < samples; i += l2) { 150 | uint16_t i1 = i + l1; 151 | double t1 = u1 * vReal[i1] - u2 * vImag[i1]; 152 | double t2 = u1 * vImag[i1] + u2 * vReal[i1]; 153 | vReal[i1] = vReal[i] - t1; 154 | vImag[i1] = vImag[i] - t2; 155 | vReal[i] += t1; 156 | vImag[i] += t2; 157 | } 158 | double z = ((u1 * c1) - (u2 * c2)); 159 | u2 = ((u1 * c2) + (u2 * c1)); 160 | u1 = z; 161 | } 162 | #ifdef __AVR__ 163 | c2 = pgm_read_float_near(&(_c2[index])); 164 | c1 = pgm_read_float_near(&(_c1[index])); 165 | index++; 166 | #else 167 | c2 = sqrt((1.0 - c1) / 2.0); 168 | c1 = sqrt((1.0 + c1) / 2.0); 169 | #endif 170 | if (dir == FFT_FORWARD) { 171 | c2 = -c2; 172 | } 173 | } 174 | // Scaling for reverse transform 175 | if (dir != FFT_FORWARD) { 176 | for (uint16_t i = 0; i < samples; i++) { 177 | vReal[i] /= samples; 178 | vImag[i] /= samples; 179 | } 180 | } 181 | } 182 | 183 | void arduinoFFT::ComplexToMagnitude() 184 | { // vM is half the size of vReal and vImag 185 | for (uint16_t i = 0; i < this->_samples; i++) { 186 | this->_vReal[i] = sqrt(sq(this->_vReal[i]) + sq(this->_vImag[i])); 187 | } 188 | } 189 | 190 | void arduinoFFT::ComplexToMagnitude(double *vReal, double *vImag, uint16_t samples) 191 | { // vM is half the size of vReal and vImag 192 | #warning("This method is deprecated and may be removed on future revisions.") 193 | for (uint16_t i = 0; i < samples; i++) { 194 | vReal[i] = sqrt(sq(vReal[i]) + sq(vImag[i])); 195 | } 196 | } 197 | 198 | void arduinoFFT::DCRemoval() 199 | { 200 | // calculate the mean of vData 201 | double mean = 0; 202 | for (uint16_t i = 1; i < ((this->_samples >> 1) + 1); i++) 203 | { 204 | mean += this->_vReal[i]; 205 | } 206 | mean /= this->_samples; 207 | // Subtract the mean from vData 208 | for (uint16_t i = 1; i < ((this->_samples >> 1) + 1); i++) 209 | { 210 | this->_vReal[i] -= mean; 211 | } 212 | } 213 | 214 | void arduinoFFT::DCRemoval(double *vData, uint16_t samples) 215 | { 216 | // calculate the mean of vData 217 | #warning("This method is deprecated and may be removed on future revisions.") 218 | double mean = 0; 219 | for (uint16_t i = 1; i < ((samples >> 1) + 1); i++) 220 | { 221 | mean += vData[i]; 222 | } 223 | mean /= samples; 224 | // Subtract the mean from vData 225 | for (uint16_t i = 1; i < ((samples >> 1) + 1); i++) 226 | { 227 | vData[i] -= mean; 228 | } 229 | } 230 | 231 | void arduinoFFT::Windowing(uint8_t windowType, uint8_t dir) 232 | {// Weighing factors are computed once before multiple use of FFT 233 | // The weighing function is symetric; half the weighs are recorded 234 | double samplesMinusOne = (double(this->_samples) - 1.0); 235 | for (uint16_t i = 0; i < (this->_samples >> 1); i++) { 236 | double indexMinusOne = double(i); 237 | double ratio = (indexMinusOne / samplesMinusOne); 238 | double weighingFactor = 1.0; 239 | // Compute and record weighting factor 240 | switch (windowType) { 241 | case FFT_WIN_TYP_RECTANGLE: // rectangle (box car) 242 | weighingFactor = 1.0; 243 | break; 244 | case FFT_WIN_TYP_HAMMING: // hamming 245 | weighingFactor = 0.54 - (0.46 * cos(twoPi * ratio)); 246 | break; 247 | case FFT_WIN_TYP_HANN: // hann 248 | weighingFactor = 0.54 * (1.0 - cos(twoPi * ratio)); 249 | break; 250 | case FFT_WIN_TYP_TRIANGLE: // triangle (Bartlett) 251 | weighingFactor = 1.0 - ((2.0 * abs(indexMinusOne - (samplesMinusOne / 2.0))) / samplesMinusOne); 252 | break; 253 | case FFT_WIN_TYP_NUTTALL: // nuttall 254 | weighingFactor = 0.355768 - (0.487396 * (cos(twoPi * ratio))) + (0.144232 * (cos(fourPi * ratio))) - (0.012604 * (cos(sixPi * ratio))); 255 | break; 256 | case FFT_WIN_TYP_BLACKMAN: // blackman 257 | weighingFactor = 0.42323 - (0.49755 * (cos(twoPi * ratio))) + (0.07922 * (cos(fourPi * ratio))); 258 | break; 259 | case FFT_WIN_TYP_BLACKMAN_NUTTALL: // blackman nuttall 260 | weighingFactor = 0.3635819 - (0.4891775 * (cos(twoPi * ratio))) + (0.1365995 * (cos(fourPi * ratio))) - (0.0106411 * (cos(sixPi * ratio))); 261 | break; 262 | case FFT_WIN_TYP_BLACKMAN_HARRIS: // blackman harris 263 | weighingFactor = 0.35875 - (0.48829 * (cos(twoPi * ratio))) + (0.14128 * (cos(fourPi * ratio))) - (0.01168 * (cos(sixPi * ratio))); 264 | break; 265 | case FFT_WIN_TYP_FLT_TOP: // flat top 266 | weighingFactor = 0.2810639 - (0.5208972 * cos(twoPi * ratio)) + (0.1980399 * cos(fourPi * ratio)); 267 | break; 268 | case FFT_WIN_TYP_WELCH: // welch 269 | weighingFactor = 1.0 - sq((indexMinusOne - samplesMinusOne / 2.0) / (samplesMinusOne / 2.0)); 270 | break; 271 | } 272 | if (dir == FFT_FORWARD) { 273 | this->_vReal[i] *= weighingFactor; 274 | this->_vReal[this->_samples - (i + 1)] *= weighingFactor; 275 | } 276 | else { 277 | this->_vReal[i] /= weighingFactor; 278 | this->_vReal[this->_samples - (i + 1)] /= weighingFactor; 279 | } 280 | } 281 | } 282 | 283 | 284 | void arduinoFFT::Windowing(double *vData, uint16_t samples, uint8_t windowType, uint8_t dir) 285 | {// Weighing factors are computed once before multiple use of FFT 286 | // The weighing function is symetric; half the weighs are recorded 287 | #warning("This method is deprecated and may be removed on future revisions.") 288 | double samplesMinusOne = (double(samples) - 1.0); 289 | for (uint16_t i = 0; i < (samples >> 1); i++) { 290 | double indexMinusOne = double(i); 291 | double ratio = (indexMinusOne / samplesMinusOne); 292 | double weighingFactor = 1.0; 293 | // Compute and record weighting factor 294 | switch (windowType) { 295 | case FFT_WIN_TYP_RECTANGLE: // rectangle (box car) 296 | weighingFactor = 1.0; 297 | break; 298 | case FFT_WIN_TYP_HAMMING: // hamming 299 | weighingFactor = 0.54 - (0.46 * cos(twoPi * ratio)); 300 | break; 301 | case FFT_WIN_TYP_HANN: // hann 302 | weighingFactor = 0.54 * (1.0 - cos(twoPi * ratio)); 303 | break; 304 | case FFT_WIN_TYP_TRIANGLE: // triangle (Bartlett) 305 | weighingFactor = 1.0 - ((2.0 * abs(indexMinusOne - (samplesMinusOne / 2.0))) / samplesMinusOne); 306 | break; 307 | case FFT_WIN_TYP_NUTTALL: // nuttall 308 | weighingFactor = 0.355768 - (0.487396 * (cos(twoPi * ratio))) + (0.144232 * (cos(fourPi * ratio))) - (0.012604 * (cos(sixPi * ratio))); 309 | break; 310 | case FFT_WIN_TYP_BLACKMAN: // blackman 311 | weighingFactor = 0.42323 - (0.49755 * (cos(twoPi * ratio))) + (0.07922 * (cos(fourPi * ratio))); 312 | break; 313 | case FFT_WIN_TYP_BLACKMAN_NUTTALL: // blackman nuttall 314 | weighingFactor = 0.3635819 - (0.4891775 * (cos(twoPi * ratio))) + (0.1365995 * (cos(fourPi * ratio))) - (0.0106411 * (cos(sixPi * ratio))); 315 | break; 316 | case FFT_WIN_TYP_BLACKMAN_HARRIS: // blackman harris 317 | weighingFactor = 0.35875 - (0.48829 * (cos(twoPi * ratio))) + (0.14128 * (cos(fourPi * ratio))) - (0.01168 * (cos(sixPi * ratio))); 318 | break; 319 | case FFT_WIN_TYP_FLT_TOP: // flat top 320 | weighingFactor = 0.2810639 - (0.5208972 * cos(twoPi * ratio)) + (0.1980399 * cos(fourPi * ratio)); 321 | break; 322 | case FFT_WIN_TYP_WELCH: // welch 323 | weighingFactor = 1.0 - sq((indexMinusOne - samplesMinusOne / 2.0) / (samplesMinusOne / 2.0)); 324 | break; 325 | } 326 | if (dir == FFT_FORWARD) { 327 | vData[i] *= weighingFactor; 328 | vData[samples - (i + 1)] *= weighingFactor; 329 | } 330 | else { 331 | vData[i] /= weighingFactor; 332 | vData[samples - (i + 1)] /= weighingFactor; 333 | } 334 | } 335 | } 336 | 337 | double arduinoFFT::MajorPeak() 338 | { 339 | double maxY = 0; 340 | uint16_t IndexOfMaxY = 0; 341 | //If sampling_frequency = 2 * max_frequency in signal, 342 | //value would be stored at position samples/2 343 | for (uint16_t i = 1; i < ((this->_samples >> 1) + 1); i++) { 344 | if ((this->_vReal[i-1] < this->_vReal[i]) && (this->_vReal[i] > this->_vReal[i+1])) { 345 | if (this->_vReal[i] > maxY) { 346 | maxY = this->_vReal[i]; 347 | IndexOfMaxY = i; 348 | } 349 | } 350 | } 351 | double delta = 0.5 * ((this->_vReal[IndexOfMaxY-1] - this->_vReal[IndexOfMaxY+1]) / (this->_vReal[IndexOfMaxY-1] - (2.0 * this->_vReal[IndexOfMaxY]) + this->_vReal[IndexOfMaxY+1])); 352 | double interpolatedX = ((IndexOfMaxY + delta) * this->_samplingFrequency) / (this->_samples-1); 353 | if(IndexOfMaxY==(this->_samples >> 1)) //To improve calculation on edge values 354 | interpolatedX = ((IndexOfMaxY + delta) * this->_samplingFrequency) / (this->_samples); 355 | // returned value: interpolated frequency peak apex 356 | return(interpolatedX); 357 | } 358 | 359 | void arduinoFFT::MajorPeak(double *f, double *v) 360 | { 361 | double maxY = 0; 362 | uint16_t IndexOfMaxY = 0; 363 | //If sampling_frequency = 2 * max_frequency in signal, 364 | //value would be stored at position samples/2 365 | for (uint16_t i = 1; i < ((this->_samples >> 1) + 1); i++) { 366 | if ((this->_vReal[i - 1] < this->_vReal[i]) && (this->_vReal[i] > this->_vReal[i + 1])) { 367 | if (this->_vReal[i] > maxY) { 368 | maxY = this->_vReal[i]; 369 | IndexOfMaxY = i; 370 | } 371 | } 372 | } 373 | double delta = 0.5 * ((this->_vReal[IndexOfMaxY - 1] - this->_vReal[IndexOfMaxY + 1]) / (this->_vReal[IndexOfMaxY - 1] - (2.0 * this->_vReal[IndexOfMaxY]) + this->_vReal[IndexOfMaxY + 1])); 374 | double interpolatedX = ((IndexOfMaxY + delta) * this->_samplingFrequency) / (this->_samples - 1); 375 | if (IndexOfMaxY == (this->_samples >> 1)) //To improve calculation on edge values 376 | interpolatedX = ((IndexOfMaxY + delta) * this->_samplingFrequency) / (this->_samples); 377 | // returned value: interpolated frequency peak apex 378 | *f = interpolatedX; 379 | *v = abs(this->_vReal[IndexOfMaxY - 1] - (2.0 * this->_vReal[IndexOfMaxY]) + this->_vReal[IndexOfMaxY + 1]); 380 | } 381 | 382 | double arduinoFFT::MajorPeak(double *vD, uint16_t samples, double samplingFrequency) 383 | { 384 | #warning("This method is deprecated and may be removed on future revisions.") 385 | double maxY = 0; 386 | uint16_t IndexOfMaxY = 0; 387 | //If sampling_frequency = 2 * max_frequency in signal, 388 | //value would be stored at position samples/2 389 | for (uint16_t i = 1; i < ((samples >> 1) + 1); i++) { 390 | if ((vD[i-1] < vD[i]) && (vD[i] > vD[i+1])) { 391 | if (vD[i] > maxY) { 392 | maxY = vD[i]; 393 | IndexOfMaxY = i; 394 | } 395 | } 396 | } 397 | double delta = 0.5 * ((vD[IndexOfMaxY-1] - vD[IndexOfMaxY+1]) / (vD[IndexOfMaxY-1] - (2.0 * vD[IndexOfMaxY]) + vD[IndexOfMaxY+1])); 398 | double interpolatedX = ((IndexOfMaxY + delta) * samplingFrequency) / (samples-1); 399 | if(IndexOfMaxY==(samples >> 1)) //To improve calculation on edge values 400 | interpolatedX = ((IndexOfMaxY + delta) * samplingFrequency) / (samples); 401 | // returned value: interpolated frequency peak apex 402 | return(interpolatedX); 403 | } 404 | 405 | void arduinoFFT::MajorPeak(double *vD, uint16_t samples, double samplingFrequency, double *f, double *v) 406 | { 407 | #warning("This method is deprecated and may be removed on future revisions.") 408 | double maxY = 0; 409 | uint16_t IndexOfMaxY = 0; 410 | //If sampling_frequency = 2 * max_frequency in signal, 411 | //value would be stored at position samples/2 412 | for (uint16_t i = 1; i < ((samples >> 1) + 1); i++) { 413 | if ((vD[i - 1] < vD[i]) && (vD[i] > vD[i + 1])) { 414 | if (vD[i] > maxY) { 415 | maxY = vD[i]; 416 | IndexOfMaxY = i; 417 | } 418 | } 419 | } 420 | double delta = 0.5 * ((vD[IndexOfMaxY - 1] - vD[IndexOfMaxY + 1]) / (vD[IndexOfMaxY - 1] - (2.0 * vD[IndexOfMaxY]) + vD[IndexOfMaxY + 1])); 421 | double interpolatedX = ((IndexOfMaxY + delta) * samplingFrequency) / (samples - 1); 422 | //double popo = 423 | if (IndexOfMaxY == (samples >> 1)) //To improve calculation on edge values 424 | interpolatedX = ((IndexOfMaxY + delta) * samplingFrequency) / (samples); 425 | // returned value: interpolated frequency peak apex 426 | *f = interpolatedX; 427 | *v = abs(vD[IndexOfMaxY - 1] - (2.0 * vD[IndexOfMaxY]) + vD[IndexOfMaxY + 1]); 428 | } 429 | 430 | uint8_t arduinoFFT::Exponent(uint16_t value) 431 | { 432 | #warning("This method may not be accessible on future revisions.") 433 | // Calculates the base 2 logarithm of a value 434 | uint8_t result = 0; 435 | while (((value >> result) & 1) != 1) result++; 436 | return(result); 437 | } 438 | 439 | // Private functions 440 | 441 | void arduinoFFT::Swap(double *x, double *y) 442 | { 443 | double temp = *x; 444 | *x = *y; 445 | *y = temp; 446 | } 447 | -------------------------------------------------------------------------------- /BM1422AGMV/arduinoFFT.h: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | FFT libray 4 | Copyright (C) 2010 Didier Longueville 5 | Copyright (C) 2014 Enrique Condes 6 | 7 | This program is free software: you can redistribute it and/or modify 8 | it under the terms of the GNU General Public License as published by 9 | the Free Software Foundation, either version 3 of the License, or 10 | (at your option) any later version. 11 | 12 | This program 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 program. If not, see . 19 | 20 | */ 21 | 22 | #ifndef arduinoFFT_h /* Prevent loading library twice */ 23 | #define arduinoFFT_h 24 | #ifdef ARDUINO 25 | #if ARDUINO >= 100 26 | #include "Arduino.h" 27 | #else 28 | #include "WProgram.h" /* This is where the standard Arduino code lies */ 29 | #endif 30 | #else 31 | #include 32 | #include 33 | #ifdef __AVR__ 34 | #include 35 | #include 36 | #endif 37 | #include 38 | #include "defs.h" 39 | #include "types.h" 40 | #endif 41 | 42 | #define FFT_LIB_REV 0x14 43 | /* Custom constants */ 44 | #define FFT_FORWARD 0x01 45 | #define FFT_REVERSE 0x00 46 | 47 | /* Windowing type */ 48 | #define FFT_WIN_TYP_RECTANGLE 0x00 /* rectangle (Box car) */ 49 | #define FFT_WIN_TYP_HAMMING 0x01 /* hamming */ 50 | #define FFT_WIN_TYP_HANN 0x02 /* hann */ 51 | #define FFT_WIN_TYP_TRIANGLE 0x03 /* triangle (Bartlett) */ 52 | #define FFT_WIN_TYP_NUTTALL 0x04 /* nuttall */ 53 | #define FFT_WIN_TYP_BLACKMAN 0x05 /* blackman */ 54 | #define FFT_WIN_TYP_BLACKMAN_NUTTALL 0x06 /* blackman nuttall */ 55 | #define FFT_WIN_TYP_BLACKMAN_HARRIS 0x07 /* blackman harris*/ 56 | #define FFT_WIN_TYP_FLT_TOP 0x08 /* flat top */ 57 | #define FFT_WIN_TYP_WELCH 0x09 /* welch */ 58 | /*Mathematial constants*/ 59 | #define twoPi 6.28318531 60 | #define fourPi 12.56637061 61 | #define sixPi 18.84955593 62 | 63 | #ifdef __AVR__ 64 | static const double _c1[]PROGMEM = {0.0000000000, 0.7071067812, 0.9238795325, 0.9807852804, 65 | 0.9951847267, 0.9987954562, 0.9996988187, 0.9999247018, 66 | 0.9999811753, 0.9999952938, 0.9999988235, 0.9999997059, 67 | 0.9999999265, 0.9999999816, 0.9999999954, 0.9999999989, 68 | 0.9999999997}; 69 | static const double _c2[]PROGMEM = {1.0000000000, 0.7071067812, 0.3826834324, 0.1950903220, 70 | 0.0980171403, 0.0490676743, 0.0245412285, 0.0122715383, 71 | 0.0061358846, 0.0030679568, 0.0015339802, 0.0007669903, 72 | 0.0003834952, 0.0001917476, 0.0000958738, 0.0000479369, 73 | 0.0000239684}; 74 | #endif 75 | class arduinoFFT { 76 | public: 77 | /* Constructor */ 78 | arduinoFFT(void); 79 | arduinoFFT(double *vReal, double *vImag, uint16_t samples, double samplingFrequency); 80 | /* Destructor */ 81 | ~arduinoFFT(void); 82 | /* Functions */ 83 | uint8_t Revision(void); 84 | uint8_t Exponent(uint16_t value); 85 | 86 | void ComplexToMagnitude(double *vReal, double *vImag, uint16_t samples); 87 | void Compute(double *vReal, double *vImag, uint16_t samples, uint8_t dir); 88 | void Compute(double *vReal, double *vImag, uint16_t samples, uint8_t power, uint8_t dir); 89 | void DCRemoval(double *vData, uint16_t samples); 90 | double MajorPeak(double *vD, uint16_t samples, double samplingFrequency); 91 | void MajorPeak(double *vD, uint16_t samples, double samplingFrequency, double *f, double *v); 92 | void Windowing(double *vData, uint16_t samples, uint8_t windowType, uint8_t dir); 93 | 94 | void ComplexToMagnitude(); 95 | void Compute(uint8_t dir); 96 | void DCRemoval(); 97 | double MajorPeak(); 98 | void MajorPeak(double *f, double *v); 99 | void Windowing(uint8_t windowType, uint8_t dir); 100 | 101 | private: 102 | /* Variables */ 103 | uint16_t _samples; 104 | double _samplingFrequency; 105 | double *_vReal; 106 | double *_vImag; 107 | uint8_t _power; 108 | /* Functions */ 109 | void Swap(double *x, double *y); 110 | }; 111 | 112 | #endif 113 | -------------------------------------------------------------------------------- /BM1422AGMV/examples/BM1422AGMV/BM1422AGMV.ino: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | BM1422AGMV.ino 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #include 25 | #include "BM1422AGMV.h" 26 | 27 | BM1422AGMV bm1422agmv(BM1422AGMV_DEVICE_ADDRESS_0F); 28 | 29 | void setup() { 30 | byte rc; 31 | 32 | Serial.begin(115200); 33 | Serial.println("Rohm BM1422AGMV Magnet Sensor sample"); 34 | Wire.begin(); 35 | rc = bm1422agmv.init(); 36 | if (rc != 0) { 37 | Serial.println(F("BM1422AGMV initialization failed")); 38 | Serial.flush(); 39 | } 40 | 41 | } 42 | 43 | void loop() { 44 | byte rc; 45 | float mag[3]; 46 | rc = bm1422agmv.get_val(mag); 47 | 48 | if (rc == 0) { 49 | Serial.print("BM1422AGMV XDATA="); 50 | Serial.print(mag[0], 3); 51 | Serial.println("[uT]"); 52 | Serial.print("BM1422AGMV YDATA="); 53 | Serial.print(mag[1], 3); 54 | Serial.println("[uT]"); 55 | Serial.print("BM1422AGMV ZDATA="); 56 | Serial.print(mag[2], 3); 57 | Serial.println("[uT]"); 58 | Serial.println(); 59 | } 60 | 61 | delay(500); 62 | } 63 | -------------------------------------------------------------------------------- /BM1422AGMV/examples/BM1422AGMV_FFT_SPRESENSE/BM1422AGMV_FFT_SPRESENSE.ino: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | BM1422AGMV_FFT_SPRESENSE.ino 3 | 4 | Copyright (c) 2020 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #include 25 | #include 26 | #include "BM1422AGMV.h" 27 | #include 28 | 29 | #define SYSTEM_BAUDRATE (115200) 30 | #define SAMPLES (256) // 2^n 31 | #define SAMPLING_FREQUENCY (600) // Hz 32 | #define harmonic_start_point (5) // ignore low frequency 33 | 34 | BM1422AGMV bm1422agmv(BM1422AGMV_DEVICE_ADDRESS_0F); 35 | void get_data(double *real_x, double *real_y, double *real_z, double *imag_x, double *imag_y, double *imag_z); 36 | void calc_FFT(double *real, double *imag); 37 | void draw_data(int32_t cnt_max, double *real_x, double *real_y, double *real_z); 38 | void draw_harmonics(double *real_x, double *real_y, double *real_z); 39 | void calc_Harmonics(double *real, int32_t *first_cnt, int32_t *second_cnt, int32_t *third_cnt); 40 | 41 | double real_x[SAMPLES], real_y[SAMPLES], real_z[SAMPLES]; 42 | double imag_x[SAMPLES], imag_y[SAMPLES], imag_z[SAMPLES]; 43 | 44 | // make FFT object 45 | arduinoFFT FFT = arduinoFFT(); 46 | 47 | void setup() 48 | { 49 | int32_t result; 50 | 51 | Serial.begin(SYSTEM_BAUDRATE); 52 | while (!Serial); 53 | 54 | Wire.begin(); 55 | 56 | result = bm1422agmv.init(); 57 | if (result != 0) { 58 | Serial.println(F("BM1422AGMV initialization failed")); 59 | Serial.flush(); 60 | } 61 | 62 | delay(100); 63 | } 64 | 65 | void loop() 66 | { 67 | get_data(real_x, real_y, real_z, imag_x, imag_y, imag_z); 68 | 69 | // for debug // draw sensor data 70 | draw_data(SAMPLES, real_x, real_y, real_z); 71 | 72 | // arduinoFFT fanctions 73 | calc_FFT(real_x, imag_x); 74 | calc_FFT(real_y, imag_y); 75 | calc_FFT(real_z, imag_z); 76 | 77 | // draw FFT data 78 | draw_data((SAMPLES/2), real_x, real_y, real_z); 79 | 80 | draw_harmonics(real_x, real_y, real_z); 81 | 82 | // for debug // single 83 | //while(1); 84 | 85 | // Loop 86 | delay(1000); 87 | } 88 | 89 | void get_data(double *real_x, double *real_y, double *real_z, double *imag_x, double *imag_y, double *imag_z) 90 | { 91 | int32_t cnt; 92 | uint32_t start_time; 93 | uint32_t sampling_time = 1.00 / SAMPLING_FREQUENCY * 1000000; 94 | float mag[3] = {0.0, 0.0, 0.0}; 95 | 96 | for(cnt = 0; cnt < SAMPLES; cnt++){ 97 | start_time = micros(); 98 | 99 | (void)bm1422agmv.get_val(mag); 100 | 101 | real_x[cnt] = (double)mag[0]; // x axsis 102 | real_y[cnt] = (double)mag[1]; // y axsis 103 | real_z[cnt] = (double)mag[2]; // z axsis 104 | 105 | imag_x[cnt] = 0; 106 | imag_y[cnt] = 0; 107 | imag_z[cnt] = 0; 108 | 109 | // wait sampling time 110 | while(micros() < (start_time + sampling_time)); 111 | } 112 | } 113 | 114 | void calc_FFT(double *real, double *imag) 115 | { 116 | FFT.DCRemoval(real, SAMPLES); 117 | FFT.Windowing(real, SAMPLES, FFT_WIN_TYP_HAMMING, FFT_FORWARD); 118 | FFT.Compute(real, imag, SAMPLES, FFT_FORWARD); 119 | FFT.ComplexToMagnitude(real, imag, SAMPLES); 120 | } 121 | 122 | void draw_data(int32_t cnt_max, double *real_x, double *real_y, double *real_z) 123 | { 124 | int32_t cnt; 125 | 126 | for (cnt = 0; cnt < cnt_max; cnt++) { 127 | Serial.print(real_x[cnt], 5); 128 | Serial.print(","); 129 | Serial.print(real_y[cnt], 5); 130 | Serial.print(","); 131 | Serial.println(real_z[cnt], 5); 132 | } 133 | 134 | Serial.println(); 135 | } 136 | 137 | void draw_harmonics(double *real_x, double *real_y, double *real_z) 138 | { 139 | int32_t cnt; 140 | float frequency[SAMPLES/2]; 141 | int32_t first_cnt, second_cnt, third_cnt; 142 | 143 | first_cnt = 0; 144 | second_cnt = 0; 145 | third_cnt = 0; 146 | 147 | for (cnt = 0; cnt < SAMPLES/2; cnt++) { 148 | frequency[cnt] = (float)SAMPLING_FREQUENCY / SAMPLES * cnt; 149 | } 150 | 151 | // x axis 152 | calc_Harmonics(real_x, &first_cnt, &second_cnt, &third_cnt); 153 | Serial.println("--- X axis harmonics ---"); 154 | Serial.print("First harmonic [Hz] : "); 155 | Serial.println(frequency[first_cnt], 5); 156 | Serial.print("Second harmonic [Hz] : "); 157 | Serial.println(frequency[second_cnt], 5); 158 | Serial.print("Third harmonic [Hz] : "); 159 | Serial.println(frequency[third_cnt], 5); 160 | Serial.println(); 161 | 162 | // y axis 163 | calc_Harmonics(real_y, &first_cnt, &second_cnt, &third_cnt); 164 | Serial.println("--- Y axis harmonics ---"); 165 | Serial.print("First harmonic [Hz] : "); 166 | Serial.println(frequency[first_cnt], 5); 167 | Serial.print("Second harmonic [Hz] : "); 168 | Serial.println(frequency[second_cnt], 5); 169 | Serial.print("Third harmonic [Hz] : "); 170 | Serial.println(frequency[third_cnt], 5); 171 | Serial.println(); 172 | 173 | // z axis 174 | calc_Harmonics(real_z, &first_cnt, &second_cnt, &third_cnt); 175 | Serial.println("--- Z axis harmonics ---"); 176 | Serial.print("First harmonic [Hz] : "); 177 | Serial.println(frequency[first_cnt], 5); 178 | Serial.print("Second harmonic [Hz] : "); 179 | Serial.println(frequency[second_cnt], 5); 180 | Serial.print("Third harmonic [Hz] : "); 181 | Serial.println(frequency[third_cnt], 5); 182 | Serial.println(); 183 | } 184 | 185 | void calc_Harmonics(double *real, int32_t *first_cnt, int32_t *second_cnt, int32_t *third_cnt) 186 | { 187 | int32_t cnt; 188 | double first_val, second_val, third_val; 189 | 190 | first_val = 0; 191 | second_val = 0; 192 | third_val = 0; 193 | 194 | for (cnt = harmonic_start_point; cnt < SAMPLES/2; cnt++) { 195 | if (real[cnt] > first_val) { 196 | first_val = real[cnt]; 197 | *first_cnt = cnt; 198 | } else if (real[cnt] > second_val) { 199 | second_val = real[cnt]; 200 | *second_cnt = cnt; 201 | } else if (real[cnt] > third_val) { 202 | third_val = real[cnt]; 203 | *third_cnt = cnt; 204 | } 205 | } 206 | } 207 | -------------------------------------------------------------------------------- /BM1422AGMV/keywords.txt: -------------------------------------------------------------------------------- 1 | BM1422AGMV KEYWORD1 2 | init KEYWORD2 3 | get_rawval KEYWORD2 4 | get_val KEYWORD2 5 | convert_uT KEYWORD2 6 | write KEYWORD2 7 | read KEYWORD2 8 | -------------------------------------------------------------------------------- /KX122/KX122.cpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | KX122.cpp 3 | Copyright (c) 2018 ROHM Co.,Ltd. 4 | Permission is hereby granted, free of charge, to any person obtaining a copy 5 | of this software and associated documentation files (the "Software"), to deal 6 | in the Software without restriction, including without limitation the rights 7 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 8 | copies of the Software, and to permit persons to whom the Software is 9 | furnished to do so, subject to the following conditions: 10 | The above copyright notice and this permission notice shall be included in 11 | all copies or substantial portions of the Software. 12 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 13 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 14 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 15 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 16 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 17 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 18 | THE SOFTWARE. 19 | ******************************************************************************/ 20 | #include 21 | #include 22 | #include "KX122.h" 23 | 24 | KX122::KX122(int slave_address) 25 | { 26 | _device_address = slave_address; 27 | } 28 | 29 | byte KX122::init(void) 30 | { 31 | byte rc; 32 | unsigned char reg; 33 | unsigned char gsel; 34 | int i; 35 | 36 | rc = read(KX122_WHO_AM_I, ®, sizeof(reg)); 37 | if (rc != 0) { 38 | Serial.println("Can't access KX122"); 39 | return (rc); 40 | } 41 | Serial.print("KX122_WHO_AMI Register Value = 0x"); 42 | Serial.println(reg, HEX); 43 | 44 | if (reg != KX122_WAI_VAL) { 45 | Serial.println("Can't find KX122"); 46 | return (-1); 47 | } 48 | 49 | reg = KX122_CNTL1_VAL; 50 | rc = write(KX122_CNTL1, ®, sizeof(reg)); 51 | if (rc != 0) { 52 | Serial.println("Can't write KX122 CNTL1 register at first"); 53 | return (rc); 54 | } 55 | 56 | reg = KX122_ODCNTL_VAL; 57 | rc = write(KX122_ODCNTL, ®, sizeof(reg)); 58 | if (rc != 0) { 59 | Serial.println("Can't write KX122 ODCNTL register"); 60 | return (rc); 61 | } 62 | 63 | rc = read(KX122_CNTL1, ®, sizeof(reg)); 64 | if (rc != 0) { 65 | Serial.println("Can't read KX122 CNTL1 register"); 66 | return (rc); 67 | } 68 | gsel = reg & KX122_CNTL1_GSELMASK; 69 | 70 | reg |= KX122_CNTL1_PC1; 71 | rc = write(KX122_CNTL1, ®, sizeof(reg)); 72 | if (rc != 0) { 73 | Serial.println("Can't write KX122 CNTL1 register at second"); 74 | return (rc); 75 | } 76 | 77 | switch(gsel) { 78 | case KX122_CNTL1_GSEL_2G : _g_sens = 16384; break; 79 | case KX122_CNTL1_GSEL_4G : _g_sens = 8192; break; 80 | case KX122_CNTL1_GSEL_8G : _g_sens = 4096; break; 81 | default: break; 82 | } 83 | 84 | return (rc); 85 | } 86 | 87 | byte KX122::get_rawval(unsigned char *data) 88 | { 89 | byte rc; 90 | 91 | rc = read(KX122_XOUT_L, data, 6); 92 | if (rc != 0) { 93 | Serial.println("Can't get KX122 accel value"); 94 | } 95 | 96 | return (rc); 97 | } 98 | 99 | byte KX122::get_val(float *data) 100 | { 101 | byte rc; 102 | unsigned char val[6]; 103 | signed short acc[3]; 104 | 105 | rc = get_rawval(val); 106 | if (rc != 0) { 107 | return (rc); 108 | } 109 | 110 | acc[0] = ((signed short)val[1] << 8) | (val[0]); 111 | acc[1] = ((signed short)val[3] << 8) | (val[2]); 112 | acc[2] = ((signed short)val[5] << 8) | (val[4]); 113 | 114 | // Convert LSB to g 115 | data[0] = (float)acc[0] / _g_sens; 116 | data[1] = (float)acc[1] / _g_sens; 117 | data[2] = (float)acc[2] / _g_sens; 118 | 119 | return (rc); 120 | } 121 | 122 | byte KX122::write(unsigned char memory_address, unsigned char *data, unsigned char size) 123 | { 124 | byte rc; 125 | unsigned int cnt; 126 | 127 | Wire.beginTransmission(_device_address); 128 | Wire.write(memory_address); 129 | Wire.write(data, size); 130 | rc = Wire.endTransmission(true); 131 | return (rc); 132 | } 133 | 134 | byte KX122::read(unsigned char memory_address, unsigned char *data, int size) 135 | { 136 | byte rc; 137 | unsigned char cnt; 138 | 139 | Wire.beginTransmission(_device_address); 140 | Wire.write(memory_address); 141 | rc = Wire.endTransmission(false); 142 | if (rc != 0) { 143 | Serial.print("Read failed!"); 144 | return (rc); 145 | } 146 | 147 | Wire.requestFrom((int)_device_address, (int)size, (int)true); 148 | cnt = 0; 149 | while(Wire.available()) { 150 | data[cnt] = Wire.read(); 151 | cnt++; 152 | } 153 | 154 | return (0); 155 | } 156 | -------------------------------------------------------------------------------- /KX122/KX122.h: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | KX122.h 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #ifndef _KX122_H_ 25 | #define _KX122_H_ 26 | 27 | #define KX122_DEVICE_ADDRESS_1E (0x1E) // 7bit Address 28 | #define KX122_DEVICE_ADDRESS_1F (0x1F) // 7bit Address 29 | #define KX122_WAI_VAL (0x1B) 30 | 31 | #define KX122_XOUT_L (0x06) 32 | #define KX122_WHO_AM_I (0x0F) 33 | #define KX122_CNTL1 (0x18) 34 | #define KX122_ODCNTL (0x1B) 35 | 36 | #define KX122_CNTL1_TPE (1 << 0) 37 | #define KX122_CNTL1_WUFE (1 << 1) 38 | #define KX122_CNTL1_TDTE (1 << 2) 39 | #define KX122_CNTL1_GSELMASK (0x18) 40 | #define KX122_CNTL1_GSEL_2G (0x00) 41 | #define KX122_CNTL1_GSEL_4G (0x08) 42 | #define KX122_CNTL1_GSEL_8G (0x10) 43 | #define KX122_CNTL1_DRDYE (1 << 5) 44 | #define KX122_CNTL1_RES (1 << 6) 45 | #define KX122_CNTL1_PC1 (1 << 7) 46 | 47 | #define KX122_ODCNTL_OSA_50HZ (2) 48 | #define KX122_ODCNTL_LPRO (1 << 6) 49 | #define KX122_IIR_BYPASS (1 << 7) 50 | 51 | #define KX122_CNTL1_VAL (KX122_CNTL1_RES | KX122_CNTL1_GSEL_2G) 52 | #define KX122_ODCNTL_VAL (KX122_ODCNTL_OSA_50HZ) 53 | 54 | class KX122 55 | { 56 | public: 57 | KX122(int slave_address); 58 | byte init(void); 59 | byte get_rawval(unsigned char *data); 60 | byte get_val(float *data); 61 | byte write(unsigned char memory_address, unsigned char *data, unsigned char size); 62 | byte read(unsigned char memory_address, unsigned char *data, int size); 63 | private: 64 | int _device_address; 65 | unsigned short _g_sens; 66 | }; 67 | 68 | #endif // _KX122_H_ 69 | -------------------------------------------------------------------------------- /KX122/examples/KX122/KX122.ino: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | KX122.ino 3 | Copyright (c) 2018 ROHM Co.,Ltd. 4 | Permission is hereby granted, free of charge, to any person obtaining a copy 5 | of this software and associated documentation files (the "Software"), to deal 6 | in the Software without restriction, including without limitation the rights 7 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 8 | copies of the Software, and to permit persons to whom the Software is 9 | furnished to do so, subject to the following conditions: 10 | The above copyright notice and this permission notice shall be included in 11 | all copies or substantial portions of the Software. 12 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 13 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 14 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 15 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 16 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 17 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 18 | THE SOFTWARE. 19 | ******************************************************************************/ 20 | #include 21 | #include "KX122.h" 22 | 23 | KX122 kx122(KX122_DEVICE_ADDRESS_1F); 24 | 25 | void setup() { 26 | byte rc; 27 | 28 | Serial.begin(115200); 29 | while (!Serial); 30 | 31 | Wire.begin(); 32 | 33 | rc = kx122.init(); 34 | if (rc != 0) { 35 | Serial.println(F("KX122 initialization failed")); 36 | Serial.flush(); 37 | } 38 | } 39 | 40 | void loop() { 41 | byte rc; 42 | float acc[3]; 43 | 44 | rc = kx122.get_val(acc); 45 | if (rc == 0) { 46 | Serial.write("KX122 (X) = "); 47 | Serial.print(acc[0]); 48 | Serial.println(" [g]"); 49 | Serial.write("KX122 (Y) = "); 50 | Serial.print(acc[1]); 51 | Serial.println(" [g]"); 52 | Serial.write("KX122 (Z) = "); 53 | Serial.print(acc[2]); 54 | Serial.println(" [g]"); 55 | Serial.println(); 56 | } 57 | 58 | delay(500); 59 | 60 | } 61 | 62 | -------------------------------------------------------------------------------- /KX122/keywords.txt: -------------------------------------------------------------------------------- 1 | KX122 KEYWORD1 2 | init KEYWORD2 3 | get_rawval KEYWORD2 4 | get_val KEYWORD2 5 | write KEYWORD2 6 | read KEYWORD2 7 | -------------------------------------------------------------------------------- /KX126/KX126.cpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | KX126.cpp 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | //#include 25 | //#include 26 | #include 27 | #include "Arduino.h" 28 | #include "KX126.h" 29 | 30 | #define RESET_DELAY 2 31 | 32 | KX126::KX126(uint8_t slave_address) 33 | { 34 | _device_address = slave_address; 35 | _g_sens = 16384; 36 | } 37 | 38 | KX126::~KX126() 39 | { 40 | _device_address = 0; 41 | _g_sens = 0; 42 | } 43 | 44 | byte KX126::init(void) 45 | { 46 | byte rc; 47 | unsigned char reg; 48 | unsigned char gsel; 49 | 50 | reg = KX126_CNTL2_SRST; 51 | rc = write(KX126_CNTL2, ®, sizeof(reg)); 52 | if (rc != 0) { 53 | Serial.println("Can't write KX126 CNTL2 register"); 54 | return (rc); 55 | } 56 | 57 | delay(RESET_DELAY); 58 | 59 | rc = read(KX126_WHO_AM_I, ®, sizeof(reg)); 60 | if (rc != 0) { 61 | Serial.println("Can't access KX126"); 62 | return (rc); 63 | } 64 | Serial.print("KX126_WHO_AMI Register Value = 0x"); 65 | Serial.println(reg, HEX); 66 | 67 | if (reg != KX126_WAI_VAL) { 68 | Serial.println("Can't find KX126"); 69 | return (-1); 70 | } 71 | 72 | reg = KX126_CNTL1_VAL; 73 | rc = write(KX126_CNTL1, ®, sizeof(reg)); 74 | if (rc != 0) { 75 | Serial.println("Can't write KX126 CNTL1 register at first"); 76 | return (rc); 77 | } 78 | 79 | reg = KX126_ODCNTL_VAL; 80 | rc = write(KX126_ODCNTL, ®, sizeof(reg)); 81 | if (rc != 0) { 82 | Serial.println("Can't write KX126 ODCNTL register"); 83 | return (rc); 84 | } 85 | 86 | rc = read(KX126_CNTL1, ®, sizeof(reg)); 87 | if (rc != 0) { 88 | Serial.println("Can't read KX126 CNTL1 register"); 89 | return (rc); 90 | } 91 | gsel = reg & KX126_CNTL1_GSELMASK; 92 | 93 | reg |= KX126_CNTL1_PC1; 94 | rc = write(KX126_CNTL1, ®, sizeof(reg)); 95 | if (rc != 0) { 96 | Serial.println("Can't write KX126 CNTL1 register at second"); 97 | return (rc); 98 | } 99 | 100 | switch(gsel) { 101 | case KX126_CNTL1_GSEL_2G : 102 | // (Equivalent counts) / (Range) = (32768 / 2) 103 | _g_sens = 16384; 104 | break; 105 | 106 | case KX126_CNTL1_GSEL_4G : 107 | // (Equivalent counts) / (Range) = (32768 / 4) 108 | _g_sens = 8192; 109 | break; 110 | 111 | case KX126_CNTL1_GSEL_8G : 112 | // (Equivalent counts) / (Range) = (32768 / 8) 113 | _g_sens = 4096; 114 | break; 115 | 116 | default: 117 | break; 118 | } 119 | return (rc); 120 | } 121 | 122 | byte KX126::get_rawval(unsigned char *data) 123 | { 124 | byte rc; 125 | 126 | rc = read(KX126_XOUT_L, data, 6); 127 | if (rc != 0) { 128 | Serial.println("Can't get KX126 accel value"); 129 | } 130 | 131 | return (rc); 132 | } 133 | 134 | byte KX126::get_val(float *data) 135 | { 136 | byte rc; 137 | unsigned char val[6]; 138 | signed short acc[3]; 139 | 140 | rc = get_rawval(val); 141 | if (rc != 0) { 142 | return (rc); 143 | } 144 | 145 | acc[0] = ((signed short)val[1] << 8) | (val[0]); 146 | acc[1] = ((signed short)val[3] << 8) | (val[2]); 147 | acc[2] = ((signed short)val[5] << 8) | (val[4]); 148 | 149 | // Convert LSB to g 150 | data[0] = (float)acc[0] / _g_sens; 151 | data[1] = (float)acc[1] / _g_sens; 152 | data[2] = (float)acc[2] / _g_sens; 153 | 154 | return (rc); 155 | } 156 | 157 | byte KX126::write(uint8_t memory_address, uint8_t *data, uint8_t len) 158 | { 159 | byte rc; 160 | 161 | Wire.beginTransmission(_device_address); 162 | Wire.write(memory_address); 163 | Wire.write(data, len); 164 | rc = Wire.endTransmission(); 165 | return (rc); 166 | } 167 | 168 | byte KX126::read(uint8_t memory_address, uint8_t *data, uint8_t len) 169 | { 170 | byte rc; 171 | unsigned char cnt; 172 | 173 | Wire.beginTransmission(_device_address); 174 | Wire.write(memory_address); 175 | rc = Wire.endTransmission(false); 176 | if (rc != 0) { 177 | return (rc); 178 | } 179 | 180 | Wire.requestFrom(_device_address, len, true); 181 | cnt = 0; 182 | while(Wire.available()) { 183 | data[cnt] = Wire.read(); 184 | cnt++; 185 | } 186 | 187 | return (0); 188 | } 189 | -------------------------------------------------------------------------------- /KX126/KX126.h: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | KX126.h 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #ifndef _KX126_H_ 25 | #define _KX126_H_ 26 | 27 | #define KX126_DEVICE_ADDRESS_1E (0x1E) // 7bit Address 28 | #define KX126_DEVICE_ADDRESS_1F (0x1F) // 7bit Address 29 | #define KX126_WAI_VAL (0x38) 30 | 31 | #define KX126_XOUT_L (0x08) 32 | #define KX126_WHO_AM_I (0x11) 33 | #define KX126_CNTL1 (0x1A) 34 | #define KX126_CNTL2 (0x1B) 35 | #define KX126_ODCNTL (0x1F) 36 | 37 | #define KX126_CNTL1_TPE (1 << 0) 38 | #define KX126_CNTL1_PDE (1 << 1) 39 | #define KX126_CNTL1_TDTE (1 << 2) 40 | #define KX126_CNTL1_GSELMASK (0x18) 41 | #define KX126_CNTL1_GSEL_2G (0x00) 42 | #define KX126_CNTL1_GSEL_4G (0x08) 43 | #define KX126_CNTL1_GSEL_8G (0x10) 44 | #define KX126_CNTL1_DRDYE (1 << 5) 45 | #define KX126_CNTL1_RES (1 << 6) 46 | #define KX126_CNTL1_PC1 (1 << 7) 47 | 48 | #define KX126_CNTL2_SRST (1 << 7) 49 | 50 | #define KX126_ODCNTL_OSA_50HZ (2) 51 | #define KX126_ODCNTL_LPRO (1 << 6) 52 | #define KX126_IIR_BYPASS (1 << 7) 53 | 54 | #define KX126_CNTL1_VAL (KX126_CNTL1_RES | KX126_CNTL1_GSEL_2G) 55 | #define KX126_ODCNTL_VAL (KX126_ODCNTL_OSA_50HZ) 56 | 57 | 58 | class KX126 59 | { 60 | public: 61 | KX126(uint8_t slave_address); 62 | ~KX126(); 63 | byte init(void); 64 | byte get_rawval(unsigned char *data); 65 | byte get_val(float *data); 66 | byte write(uint8_t memory_address, uint8_t *data, uint8_t len); 67 | byte read(uint8_t memory_address, uint8_t *data, uint8_t len); 68 | private: 69 | uint8_t _device_address; 70 | unsigned short _g_sens; 71 | }; 72 | 73 | #endif // _KX126_H_ 74 | -------------------------------------------------------------------------------- /KX126/examples/KX126/KX126.ino: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | KX126_I2C.ino 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #include 25 | #include "KX126.h" 26 | 27 | KX126 KX126(KX126_DEVICE_ADDRESS_1F); 28 | 29 | void setup() { 30 | byte rc; 31 | 32 | Serial.begin(115200); 33 | while (!Serial); 34 | 35 | Wire.begin(); 36 | 37 | rc = KX126.init(); 38 | if (rc != 0) { 39 | Serial.println("KX126 initialization failed"); 40 | Serial.flush(); 41 | } 42 | } 43 | 44 | void loop() { 45 | byte rc; 46 | float acc[3]; 47 | 48 | rc = KX126.get_val(acc); 49 | if (rc == 0) { 50 | Serial.write("KX126 (X) = "); 51 | Serial.print(acc[0]); 52 | Serial.println(" [g]"); 53 | Serial.write("KX126 (Y) = "); 54 | Serial.print(acc[1]); 55 | Serial.println(" [g]"); 56 | Serial.write("KX126 (Z) = "); 57 | Serial.print(acc[2]); 58 | Serial.println(" [g]"); 59 | Serial.println(); 60 | } 61 | 62 | delay(500); 63 | 64 | } 65 | -------------------------------------------------------------------------------- /KX126/keywords.txt: -------------------------------------------------------------------------------- 1 | KX126 KEYWORD1 2 | init KEYWORD2 3 | get_rawval KEYWORD2 4 | get_val KEYWORD2 5 | write KEYWORD2 6 | read KEYWORD2 7 | -------------------------------------------------------------------------------- /KX224/KX224.cpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | KX224.cpp 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | //#include 25 | #include 26 | #include 27 | #include "KX224.h" 28 | 29 | KX224::KX224(int slave_address) 30 | { 31 | _device_address = slave_address; 32 | _g_sens = 4096; 33 | } 34 | 35 | KX224::~KX224() 36 | { 37 | _device_address = 0; 38 | _g_sens = 0; 39 | } 40 | 41 | byte KX224::init(void) 42 | { 43 | byte rc; 44 | unsigned char reg; 45 | unsigned char gsel; 46 | 47 | rc = read(KX224_WHO_AM_I, ®, sizeof(reg)); 48 | if (rc != 0) { 49 | Serial.println("Can't access KX224"); 50 | return (rc); 51 | } 52 | Serial.print("KX224_WHO_AMI Register Value = 0x"); 53 | Serial.println(reg, HEX); 54 | 55 | if (reg != KX224_WAI_VAL) { 56 | Serial.println("Can't find KX224"); 57 | return (rc); 58 | } 59 | 60 | reg = KX224_CNTL1_VAL; 61 | rc = write(KX224_CNTL1, ®, sizeof(reg)); 62 | if (rc != 0) { 63 | Serial.println("Can't write KX224 CNTL1 register at first"); 64 | return (rc); 65 | } 66 | 67 | reg = KX224_ODCNTL_VAL; 68 | rc = write(KX224_ODCNTL, ®, sizeof(reg)); 69 | if (rc != 0) { 70 | Serial.println("Can't write KX224 ODCNTL register"); 71 | return (rc); 72 | } 73 | 74 | rc = read(KX224_CNTL1, ®, sizeof(reg)); 75 | if (rc != 0) { 76 | Serial.println("Can't read KX224 CNTL1 register"); 77 | return (rc); 78 | } 79 | gsel = reg & KX224_CNTL1_GSELMASK; 80 | 81 | reg |= KX224_CNTL1_PC1; 82 | rc = write(KX224_CNTL1, ®, sizeof(reg)); 83 | if (rc != 0) { 84 | Serial.println("Can't write KX224 CNTL1 register at second"); 85 | return (rc); 86 | } 87 | 88 | switch(gsel) { 89 | case KX224_CNTL1_GSEL_8G : 90 | // (Equivalent counts) / (Range) = (32768 / 8) 91 | _g_sens = 4096; 92 | break; 93 | 94 | case KX224_CNTL1_GSEL_16G : 95 | // (Equivalent counts) / (Range) = (32768 / 16) 96 | _g_sens = 2048; 97 | break; 98 | 99 | case KX224_CNTL1_GSEL_32G : 100 | // (Equivalent counts) / (Range) = (32768 / 32) 101 | _g_sens = 1024; 102 | break; 103 | 104 | default: 105 | break; 106 | } 107 | return (rc); 108 | } 109 | 110 | byte KX224::get_rawval(unsigned char *data) 111 | { 112 | byte rc; 113 | 114 | rc = read(KX224_XOUT_L, data, 6); 115 | if (rc != 0) { 116 | Serial.println("Can't get KX224 accel value"); 117 | } 118 | 119 | return (rc); 120 | } 121 | 122 | byte KX224::get_val(float *data) 123 | { 124 | byte rc; 125 | unsigned char val[6]; 126 | signed short acc[3]; 127 | 128 | rc = get_rawval(val); 129 | if (rc != 0) { 130 | return (rc); 131 | } 132 | 133 | acc[0] = ((signed short)val[1] << 8) | (val[0]); 134 | acc[1] = ((signed short)val[3] << 8) | (val[2]); 135 | acc[2] = ((signed short)val[5] << 8) | (val[4]); 136 | 137 | // Convert LSB to g 138 | data[0] = (float)acc[0] / _g_sens; 139 | data[1] = (float)acc[1] / _g_sens; 140 | data[2] = (float)acc[2] / _g_sens; 141 | 142 | return (rc); 143 | } 144 | 145 | byte KX224::write(unsigned char memory_address, unsigned char *data, unsigned char size) 146 | { 147 | byte rc; 148 | 149 | Wire.beginTransmission(_device_address); 150 | Wire.write(memory_address); 151 | Wire.write(data, size); 152 | rc = Wire.endTransmission(true); 153 | return (rc); 154 | } 155 | 156 | byte KX224::read(unsigned char memory_address, unsigned char *data, int size) 157 | { 158 | byte rc; 159 | unsigned char cnt; 160 | 161 | Wire.beginTransmission(_device_address); 162 | Wire.write(memory_address); 163 | rc = Wire.endTransmission(false); 164 | if (rc != 0) { 165 | return (rc); 166 | } 167 | 168 | Wire.requestFrom(_device_address, size, true); 169 | cnt = 0; 170 | while(Wire.available()) { 171 | data[cnt] = Wire.read(); 172 | cnt++; 173 | } 174 | 175 | return (0); 176 | } 177 | -------------------------------------------------------------------------------- /KX224/KX224.h: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | KX224.h 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #ifndef _KX224_H_ 25 | #define _KX224_H_ 26 | 27 | #define KX224_DEVICE_ADDRESS_1E (0x1E) // 7bit Addrss 28 | #define KX224_DEVICE_ADDRESS_1F (0x1F) // 7bit Address 29 | #define KX224_WAI_VAL (0x2B) 30 | 31 | #define KX224_XOUT_L (0x06) 32 | #define KX224_WHO_AM_I (0x0F) 33 | #define KX224_CNTL1 (0x18) 34 | #define KX224_ODCNTL (0x1B) 35 | 36 | #define KX224_CNTL1_TPE (1 << 0) 37 | #define KX224_CNTL1_WUFE (1 << 1) 38 | #define KX224_CNTL1_TDTE (1 << 2) 39 | #define KX224_CNTL1_GSELMASK (0x18) 40 | #define KX224_CNTL1_GSEL_8G (0x00) 41 | #define KX224_CNTL1_GSEL_16G (0x08) 42 | #define KX224_CNTL1_GSEL_32G (0x10) 43 | #define KX224_CNTL1_DRDYE (1 << 5) 44 | #define KX224_CNTL1_RES (1 << 6) 45 | #define KX224_CNTL1_PC1 (1 << 7) 46 | 47 | #define KX224_ODCNTL_OSA_50HZ (2) 48 | #define KX224_ODCNTL_LPRO (1 << 6) 49 | #define KX224_IIR_BYPASS (1 << 7) 50 | 51 | #define KX224_CNTL1_VAL (KX224_CNTL1_RES | KX224_CNTL1_GSEL_8G) 52 | #define KX224_ODCNTL_VAL (KX224_ODCNTL_OSA_50HZ) 53 | 54 | 55 | class KX224 56 | { 57 | public: 58 | KX224(int slave_address); 59 | ~KX224(); 60 | byte init(void); 61 | byte get_rawval(unsigned char *data); 62 | byte get_val(float *data); 63 | byte write(unsigned char memory_address, unsigned char *data, unsigned char size); 64 | byte read(unsigned char memory_address, unsigned char *data, int size); 65 | private: 66 | int _device_address; 67 | unsigned short _g_sens; 68 | }; 69 | 70 | #endif // _KX224_H_ 71 | -------------------------------------------------------------------------------- /KX224/examples/KX224/KX224.ino: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | KX224_I2C.ino 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #include 25 | #include "KX224.h" 26 | 27 | KX224 kx224(KX224_DEVICE_ADDRESS_1E); 28 | 29 | void setup() { 30 | byte rc; 31 | 32 | Serial.begin(115200); 33 | while (!Serial); 34 | 35 | Wire.begin(); 36 | 37 | rc = kx224.init(); 38 | if (rc != 0) { 39 | Serial.println("KX224 initialization failed"); 40 | Serial.flush(); 41 | } 42 | } 43 | 44 | void loop() { 45 | byte rc; 46 | float acc[3]; 47 | 48 | rc = kx224.get_val(acc); 49 | if (rc == 0) { 50 | Serial.write("KX224 (X) = "); 51 | Serial.print(acc[0]); 52 | Serial.println(" [g]"); 53 | Serial.write("KX224 (Y) = "); 54 | Serial.print(acc[1]); 55 | Serial.println(" [g]"); 56 | Serial.write("KX224 (Z) = "); 57 | Serial.print(acc[2]); 58 | Serial.println(" [g]"); 59 | Serial.println(); 60 | } 61 | 62 | delay(500); 63 | 64 | } 65 | -------------------------------------------------------------------------------- /KX224/keywords.txt: -------------------------------------------------------------------------------- 1 | KX224 KEYWORD1 2 | init KEYWORD2 3 | get_rawval KEYWORD2 4 | get_val KEYWORD2 5 | write KEYWORD2 6 | read KEYWORD2 7 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2018 KokiOkada 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /MK71251-02/MK71251.cpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | MK71251.cpp 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | 25 | #include "Arduino.h" 26 | #include "MK71251.h" 27 | 28 | 29 | MK71251::MK71251(void) 30 | { 31 | 32 | } 33 | 34 | byte MK71251::init(void) 35 | { 36 | 37 | // configure Output for GPIO3 (High: HCI mode, Low: AT command mode) 38 | pinMode(PIN_D21, OUTPUT); 39 | digitalWrite(PIN_D21, LOW); 40 | 41 | // reset BLE chip 42 | delay(500); 43 | pinMode(PIN_D20, OUTPUT); 44 | digitalWrite(PIN_D20, LOW); 45 | delay(10); 46 | digitalWrite(PIN_D20, HIGH); 47 | delay(20); 48 | 49 | Serial2.begin(57600); 50 | 51 | printf("MK71251-02: waiting for CTS:LOW...\n"); 52 | 53 | while (1) { 54 | int cts = digitalRead(PIN_D27); 55 | if (!cts) break; 56 | } 57 | 58 | printf("MK71251-02: CTS:LOW read succesfully\n"); 59 | 60 | // define advertising data 61 | // 020106 -> Flags: LE General Discoverable Mode, BR/EDR Not Supported 62 | // 05030f18180a -> Complete List of 16bit Service UUIDs: 180f, 180a 63 | // 09084c61706973446576 -> Complete Local Name: LapisDev 64 | Serial2.write("ATS150=02010605030f180a1809084c61706973446576\r\n"); 65 | 66 | // start advertising 67 | Serial2.write("ATD\r\n"); 68 | 69 | printf("MK71251-02: waiting for connection...\n"); 70 | 71 | while (1) { 72 | int ret = waitConnect(); 73 | if (ret) break; 74 | } 75 | 76 | printf("MK71251-02: connected succesfully\n"); 77 | 78 | return (0); 79 | } 80 | 81 | byte MK71251::write(unsigned char *data) 82 | { 83 | int rc; 84 | rc = Serial2.write(*data); 85 | if (rc != 0) { 86 | return (0); 87 | } 88 | else { 89 | return (-1); 90 | } 91 | } 92 | 93 | byte MK71251::read(unsigned char *data) 94 | { 95 | char c; 96 | if ((c = Serial2.read()) && c != 255) { 97 | *data = c; 98 | return (0); 99 | } 100 | else { 101 | return (-1); 102 | } 103 | } 104 | 105 | int MK71251::waitConnect(void) 106 | { 107 | char c = 0; 108 | char ret[128]; 109 | int n; 110 | 111 | for (n = 0; n < 128 && c != '\n';) 112 | { 113 | c = Serial2.read(); 114 | if (c != 0 && c != 255) { 115 | ret[n] = c; 116 | n++; 117 | } 118 | } 119 | ret[n - 2] = '\0'; 120 | int cmp = strcmp(ret, "CONNECT"); 121 | return cmp == 0 ? 1 : 0; 122 | } 123 | -------------------------------------------------------------------------------- /MK71251-02/MK71251.h: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | MK71251.h 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | 25 | #ifndef _MK71251_H_ 26 | #define _MK71251_H_ 27 | 28 | class MK71251 29 | { 30 | public: 31 | MK71251(void); 32 | byte init(void); 33 | byte write(unsigned char *data); 34 | byte read(unsigned char *data); 35 | private: 36 | int waitConnect(void); 37 | }; 38 | 39 | #endif // _MK71251_H_ 40 | -------------------------------------------------------------------------------- /MK71251-02/examples/MK71251-02/MK71251-02.ino: -------------------------------------------------------------------------------- 1 | #include 2 | #include "MK71251.h" 3 | #include 4 | 5 | MK71251 mk71251; 6 | 7 | void setup() { 8 | // put your setup code here, to run once: 9 | mk71251.init(); 10 | } 11 | 12 | void loop() { 13 | // put your main code here, to run repeatedly: 14 | unsigned char data, d; 15 | const char str[13] = "WRITING TEST"; 16 | int rc; 17 | 18 | // rc = 0, if data is available on Serial2, else rc = -1 19 | rc = mk71251.read(&data); 20 | 21 | if (rc == 0){ 22 | printf("Read %c\n",data); 23 | 24 | if (data == 'Z') { //Test write function when 'Z' is detected 25 | for (unsigned int i = 0; i <= strlen(str); i++) { 26 | d = str[i]; 27 | mk71251.write(&d); 28 | } 29 | } 30 | } 31 | } 32 | -------------------------------------------------------------------------------- /MK71251-02/keywords.txt: -------------------------------------------------------------------------------- 1 | MK71251 KEYWORD1 2 | init KEYWORD2 3 | write KEYWORD2 4 | read KEYWORD2 5 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Overview of this repository 2 | Arduino libraries and samples for Rohm Sensors, Wi-SUN, & Bluetooth LE 3 | 4 | ## Supported devices 5 | * Accelerometer KX122, I2C, SAD=0x1F 6 | * Accelerometer KX126, I2C, SAD=0x1F 7 | * Accelerometer KX132, I2C, SAD=0x1F 8 | * Accelerometer KX224, I2C, SAD=0x1E*/0x1F 9 | * Magnetosensor BM1422AGMV, I2C, SAD=0x0F 10 | * Pressure sensor BM1383AGLV, I2C, SAD=0x5D 11 | * Color sensor BH1749NUC, I2C, SAD=0x38/0x39* 12 | * ALS/Proximity sensor RPR-0521RS, I2C, SAD=0x38 13 | * Hall Effect sensor BD7411G, GPIO 14 | * Wi-SUN BP35C0, UART 15 | * Bluetooth LE MK71251-02, UART 16 | 17 | *Boldened is default device address 18 | 19 | ## Pin assignment for Sensor and BLE Add-on boards 20 | 21 | ### BLE Add-on board: 22 | 23 | ![](images/ble_pins2.jpg) 24 | 25 | ### Sensor Add-on board: 26 | 27 | ![](images/sens_pins2.jpg) 28 | 29 | ## How to setup and test devices with Sony Spresense 30 | 31 | About Sony Spresense 32 | https://developer.sony.com/develop/spresense/ 33 | 34 | 35 | For help regarding the installation of the Arduino IDE please refer to 36 | [Setting up the Arduino IDE](https://developer.sony.com/develop/spresense/developer-tools/get-started-using-arduino-ide/set-up-the-arduino-ide/ "Title") 37 | 38 | The example sketches are located in the same directory as the drivers. 39 | 40 | The evaluation board sensors can be attached to the Sensor Add-on board, and should work without problems. 41 | 42 | ### Installing the sensor & BLE example sketches ### 43 | 44 | For help regarding the installation of driver library to Arduino IDE please refer to 45 | [Installing driver library and examples](https://www.arduino.cc/en/Guide/Libraries/ "Title") 46 | 47 | ![](images/add_library.png) 48 | 49 | 1. You can upload the example sketch to your Spresense board by clicking Upload 50 | * If the upload fails for some reason, you may need to reset your board or unplug and plug it back in 51 | 2. After the sketch has finished uploading, open the serial monitor by clicking Tools -> Serial Monitor or use the hotkey Ctrl+Shift+M 52 | 53 | ![](images/arduino_ide.png) 54 | 55 | 3. The sketch should start, if not, please reset the board by pressing the reboot button on the main board 56 | 4. To receive the correct data on the serial monitor, please ensure that the baud rate on the serial monitor is set correctly, usually to 115200 57 | 58 | ![](images/serial_monitor.png) 59 | 60 | ### Testing the bluetooth module 61 | 62 | You need to download the LAPIS BLE tool for your phone to test the module. 63 | 64 | 1. Open the MK71251-02 sketch, upload it and open the serial monitor 65 | 2. Open the LAPIS BLE tool on your phone, and enable bluetooth 66 | 3. Locate the MK71251-02 on the list of devices 67 | * If you do not see it on the list, you may need to reboot your board 68 | 4. Connect to the module 69 | 5. Open the serial port profile 70 | * Anything you type should show up on the serial monitor 71 | * If you type 'Z', the serial port profile should show 'WRITING TEST' 72 | 73 | 74 | 75 | 76 | -------------------------------------------------------------------------------- /RPR-0521RS/RPR-0521RS.cpp: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | RPR-0521RS.cpp 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | //#include 25 | #include 26 | #include 27 | #include "RPR-0521RS.h" 28 | 29 | RPR0521RS::RPR0521RS(void) 30 | { 31 | 32 | } 33 | 34 | byte RPR0521RS::init(void) 35 | { 36 | byte rc; 37 | unsigned char reg; 38 | unsigned char index; 39 | unsigned char als_gain_table[] = {1, 2, 64, 128}; 40 | unsigned short als_meas_time_table[] = {0,0,0,0,0,100,100,100,100,100,400,400,50,0,0,0}; 41 | 42 | rc = read(RPR0521RS_SYSTEM_CONTROL, ®, sizeof(reg)); 43 | if (rc != 0) { 44 | Serial.println("Can't access RPR0521RS"); 45 | return (rc); 46 | } 47 | reg &= 0x3F; 48 | Serial.print("RPR0521RS Part ID Register Value = 0x"); 49 | Serial.println(reg, HEX); 50 | 51 | if (reg != RPR0521RS_PART_ID_VAL) { 52 | Serial.println("Can't find RPR0521RS"); 53 | return (rc); 54 | } 55 | 56 | rc = read(RPR0521RS_MANUFACT_ID, ®, sizeof(reg)); 57 | if (rc != 0) { 58 | Serial.println("Can't access RPR0521RS"); 59 | return (rc); 60 | } 61 | Serial.print("RPR0521RS MANUFACT_ID Register Value = 0x"); 62 | Serial.println(reg, HEX); 63 | 64 | if (reg != RPR0521RS_MANUFACT_ID_VAL) { 65 | Serial.println("Can't find RPR0521RS"); 66 | return (rc); 67 | } 68 | 69 | reg = RPR0521RS_ALS_PS_CONTROL_VAL; 70 | rc = write(RPR0521RS_ALS_PS_CONTROL, ®, sizeof(reg)); 71 | if (rc != 0) { 72 | Serial.println("Can't write RPR0521RS ALS_PS_CONTROL register"); 73 | return (rc); 74 | } 75 | 76 | rc = read(RPR0521RS_PS_CONTROL, ®, sizeof(reg)); 77 | if (rc != 0) { 78 | Serial.println("Can't read RPR0521RS PS_CONTROL register"); 79 | return (rc); 80 | } 81 | 82 | reg |= RPR0521RS_PS_CONTROL_VAL; 83 | rc = write(RPR0521RS_PS_CONTROL, ®, sizeof(reg)); 84 | if (rc != 0) { 85 | Serial.println("Can't write RPR0521RS PS_CONTROL register"); 86 | } 87 | 88 | reg = RPR0521RS_MODE_CONTROL_VAL; 89 | rc = write(RPR0521RS_MODE_CONTROL, ®, sizeof(reg)); 90 | if (rc != 0) { 91 | Serial.println("Can't write RPR0521RS MODE CONTROL register"); 92 | return (rc); 93 | } 94 | 95 | reg = RPR0521RS_ALS_PS_CONTROL_VAL; 96 | index = (reg >> 4) & 0x03; 97 | _als_data0_gain = als_gain_table[index]; 98 | index = (reg >> 2) & 0x03; 99 | _als_data1_gain = als_gain_table[index]; 100 | 101 | index = RPR0521RS_MODE_CONTROL_VAL & 0x0F; 102 | _als_measure_time = als_meas_time_table[index]; 103 | 104 | return (rc); 105 | } 106 | 107 | byte RPR0521RS::get_rawpsalsval(unsigned char *data) 108 | { 109 | byte rc; 110 | 111 | rc = read(RPR0521RS_PS_DATA_LSB, data, 6); 112 | if (rc != 0) { 113 | Serial.println("Can't get RPR0521RS PS/ALS_DATA value"); 114 | } 115 | 116 | return (rc); 117 | } 118 | 119 | byte RPR0521RS::get_psalsval(unsigned short *ps, float *als) 120 | { 121 | byte rc; 122 | unsigned char val[6]; 123 | unsigned short rawps; 124 | unsigned short rawals[2]; 125 | 126 | rc = get_rawpsalsval(val); 127 | if (rc != 0) { 128 | return (rc); 129 | } 130 | 131 | rawps = ((unsigned short)val[1] << 8) | val[0]; 132 | rawals[0] = ((unsigned short)val[3] << 8) | val[2]; 133 | rawals[1] = ((unsigned short)val[5] << 8) | val[4]; 134 | 135 | *ps = rawps; 136 | *als = convert_lx(rawals); 137 | 138 | return (rc); 139 | } 140 | 141 | byte RPR0521RS::check_near_far(unsigned short data) 142 | { 143 | if (data >= RPR0521RS_NEAR_THRESH) { 144 | return (RPR0521RS_NEAR_VAL); 145 | } else { 146 | return (RPR0521RS_FAR_VAL); 147 | } 148 | } 149 | 150 | float RPR0521RS::convert_lx(unsigned short *data) 151 | { 152 | float lx; 153 | float d0, d1, d1_d0; 154 | 155 | if (_als_data0_gain == 0) { 156 | return (RPR0521RS_ERROR); 157 | } 158 | 159 | if (_als_data1_gain == 0) { 160 | return (RPR0521RS_ERROR); 161 | } 162 | 163 | if (_als_measure_time == 0) { 164 | return (RPR0521RS_ERROR); 165 | } else if (_als_measure_time == 50) { 166 | if ((data[0] & 0x8000) == 0x8000) { 167 | data[0] = 0x7FFF; 168 | } 169 | if ((data[1] & 0x8000) == 0x8000) { 170 | data[1] = 0x7FFF; 171 | } 172 | } 173 | 174 | d0 = (float)data[0] * (100 / _als_measure_time) / _als_data0_gain; 175 | d1 = (float)data[1] * (100 / _als_measure_time) / _als_data1_gain; 176 | 177 | if (d0 == 0) { 178 | lx = 0; 179 | return (lx); 180 | } 181 | 182 | d1_d0 = d1 / d0; 183 | 184 | if (d1_d0 < 0.595) { 185 | lx = (1.682 * d0 - 1.877 * d1); 186 | } else if (d1_d0 < 1.015) { 187 | lx = (0.644 * d0 - 0.132 * d1); 188 | } else if (d1_d0 < 1.352) { 189 | lx = (0.756 * d0 - 0.243 * d1); 190 | } else if (d1_d0 < 3.053) { 191 | lx = (0.766 * d0 - 0.25 * d1); 192 | } else { 193 | lx = 0; 194 | } 195 | 196 | return (lx); 197 | } 198 | 199 | byte RPR0521RS::write(unsigned char memory_address, unsigned char *data, unsigned char size) 200 | { 201 | byte rc; 202 | 203 | Wire.beginTransmission(RPR0521RS_DEVICE_ADDRESS); 204 | Wire.write(memory_address); 205 | Wire.write(data, size); 206 | rc = Wire.endTransmission(); 207 | return (rc); 208 | } 209 | 210 | byte RPR0521RS::read(unsigned char memory_address, unsigned char *data, int size) 211 | { 212 | byte rc; 213 | unsigned char cnt; 214 | 215 | Wire.beginTransmission(RPR0521RS_DEVICE_ADDRESS); 216 | Wire.write(memory_address); 217 | rc = Wire.endTransmission(false); 218 | if (rc != 0) { 219 | return (rc); 220 | } 221 | 222 | Wire.requestFrom(RPR0521RS_DEVICE_ADDRESS, size, true); 223 | cnt = 0; 224 | while(Wire.available()) { 225 | data[cnt] = Wire.read(); 226 | cnt++; 227 | } 228 | 229 | return (0); 230 | } 231 | -------------------------------------------------------------------------------- /RPR-0521RS/RPR-0521RS.h: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | RPR-0521RS.h 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #ifndef _RPR0521RS_H_ 25 | #define _RPR0521RS_H_ 26 | 27 | #define RPR0521RS_DEVICE_ADDRESS (0x38) // 7bit Addrss 28 | #define RPR0521RS_PART_ID_VAL (0x0A) 29 | #define RPR0521RS_MANUFACT_ID_VAL (0xE0) 30 | 31 | #define RPR0521RS_SYSTEM_CONTROL (0x40) 32 | #define RPR0521RS_MODE_CONTROL (0x41) 33 | #define RPR0521RS_ALS_PS_CONTROL (0x42) 34 | #define RPR0521RS_PS_CONTROL (0x43) 35 | #define RPR0521RS_PS_DATA_LSB (0x44) 36 | #define RPR0521RS_ALS_DATA0_LSB (0x46) 37 | #define RPR0521RS_MANUFACT_ID (0x92) 38 | 39 | #define RPR0521RS_MODE_CONTROL_MEASTIME_100_100MS (6 << 0) 40 | #define RPR0521RS_MODE_CONTROL_PS_EN (1 << 6) 41 | #define RPR0521RS_MODE_CONTROL_ALS_EN (1 << 7) 42 | 43 | #define RPR0521RS_ALS_PS_CONTROL_LED_CURRENT_100MA (2 << 0) 44 | #define RPR0521RS_ALS_PS_CONTROL_DATA1_GAIN_X1 (0 << 2) 45 | #define RPR0521RS_ALS_PS_CONTROL_DATA0_GAIN_X1 (0 << 4) 46 | 47 | #define RPR0521RS_PS_CONTROL_PS_GAINX1 (0 << 4) 48 | 49 | #define RPR0521RS_MODE_CONTROL_VAL (RPR0521RS_MODE_CONTROL_MEASTIME_100_100MS | RPR0521RS_MODE_CONTROL_PS_EN | RPR0521RS_MODE_CONTROL_ALS_EN) 50 | #define RPR0521RS_ALS_PS_CONTROL_VAL (RPR0521RS_ALS_PS_CONTROL_DATA0_GAIN_X1 | RPR0521RS_ALS_PS_CONTROL_DATA1_GAIN_X1 | RPR0521RS_ALS_PS_CONTROL_LED_CURRENT_100MA) 51 | #define RPR0521RS_PS_CONTROL_VAL (RPR0521RS_PS_CONTROL_PS_GAINX1) 52 | 53 | #define RPR0521RS_NEAR_THRESH (1000) // example value 54 | #define RPR0521RS_FAR_VAL (0) 55 | #define RPR0521RS_NEAR_VAL (1) 56 | 57 | #define RPR0521RS_ERROR (-1) 58 | 59 | class RPR0521RS 60 | { 61 | public: 62 | RPR0521RS(void); 63 | byte init(void) ; 64 | byte get_rawpsalsval(unsigned char *data); 65 | byte get_psalsval(unsigned short *ps, float *als); 66 | byte check_near_far(unsigned short data); 67 | float convert_lx(unsigned short *data); 68 | byte write(unsigned char memory_address, unsigned char *data, unsigned char size); 69 | byte read(unsigned char memory_address, unsigned char *data, int size); 70 | private: 71 | unsigned short _als_data0_gain; 72 | unsigned short _als_data1_gain; 73 | unsigned short _als_measure_time; 74 | }; 75 | 76 | #endif // _RPR0521RS_H_ 77 | -------------------------------------------------------------------------------- /RPR-0521RS/examples/RPR-0521RS/RPR-0521RS.ino: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | RPR-0521RS.ino 3 | 4 | Copyright (c) 2018 ROHM Co.,Ltd. 5 | 6 | Permission is hereby granted, free of charge, to any person obtaining a copy 7 | of this software and associated documentation files (the "Software"), to deal 8 | in the Software without restriction, including without limitation the rights 9 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 | copies of the Software, and to permit persons to whom the Software is 11 | furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | ******************************************************************************/ 24 | #include 25 | #include "RPR-0521RS.h" 26 | 27 | RPR0521RS rpr0521rs; 28 | 29 | void setup() { 30 | byte rc; 31 | 32 | Serial.begin(115200); 33 | while (!Serial); 34 | 35 | Wire.begin(); 36 | 37 | rc = rpr0521rs.init(); 38 | } 39 | 40 | void loop() { 41 | byte rc; 42 | unsigned short ps_val; 43 | float als_val; 44 | byte near_far; 45 | 46 | rc = rpr0521rs.get_psalsval(&ps_val, &als_val); 47 | if (rc == 0) { 48 | Serial.print("RPR-0521RS (Proximity) = "); 49 | Serial.print(ps_val); 50 | Serial.print(" [count]"); 51 | near_far = rpr0521rs.check_near_far(ps_val); 52 | if (near_far == RPR0521RS_NEAR_VAL) { 53 | Serial.println(" Near"); 54 | } else { 55 | Serial.println(" Far"); 56 | } 57 | 58 | if (als_val != RPR0521RS_ERROR) { 59 | Serial.print("RPR-0521RS (Ambient Light) = "); 60 | Serial.print(als_val); 61 | Serial.println(" [lx]"); 62 | Serial.println(); 63 | } 64 | } 65 | 66 | delay(500); 67 | 68 | } 69 | -------------------------------------------------------------------------------- /RPR-0521RS/keywords.txt: -------------------------------------------------------------------------------- 1 | RPR0521RS KEYWORD1 2 | init KEYWORD2 3 | get_rawpsalsval KEYWORD2 4 | get_psalsval KEYWORD2 5 | check_near_far KEYWORD2 6 | convert_lx KEYWORD2 7 | write KEYWORD2 8 | read KEYWORD2 9 | -------------------------------------------------------------------------------- /SPRESENSE-Add-on-board/BOM_BLE_Add-on.xlsx: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RohmSemiconductor/Arduino/447c576a4ff34215adaf2ae0e5ea68fbc4d73b8f/SPRESENSE-Add-on-board/BOM_BLE_Add-on.xlsx -------------------------------------------------------------------------------- /SPRESENSE-Add-on-board/BOM_Sensor_Add-on.xlsx: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RohmSemiconductor/Arduino/447c576a4ff34215adaf2ae0e5ea68fbc4d73b8f/SPRESENSE-Add-on-board/BOM_Sensor_Add-on.xlsx -------------------------------------------------------------------------------- /SPRESENSE-Add-on-board/SPRESENSE_BLE_add-on_Board.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RohmSemiconductor/Arduino/447c576a4ff34215adaf2ae0e5ea68fbc4d73b8f/SPRESENSE-Add-on-board/SPRESENSE_BLE_add-on_Board.pdf -------------------------------------------------------------------------------- /SPRESENSE-Add-on-board/SPRESENSE_Sensor_add-on_Board.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RohmSemiconductor/Arduino/447c576a4ff34215adaf2ae0e5ea68fbc4d73b8f/SPRESENSE-Add-on-board/SPRESENSE_Sensor_add-on_Board.pdf -------------------------------------------------------------------------------- /SPRESENSE-WISUN-EVK-701/bp35c0-j11.cpp: -------------------------------------------------------------------------------- 1 | /******************************************************************************** 2 | bp35c0-j11.cpp 3 | Copyright (c) 2019 ROHM Co.,Ltd. 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. 22 | *********************************************************************************/ 23 | #include 24 | #include "bp35c0-j11.h" 25 | 26 | unsigned const char uni_req[4] = {0xD0 , 0xEA , 0x83 , 0xFC}; 27 | unsigned const char uni_res[4] = {0xD0 , 0xF9 , 0xEE , 0x5D}; 28 | 29 | unsigned const char ini_data[4] = {0x03 , 0x00 , 0x05 , 0x00}; // エンドデバイス/Sleep 非対応/922.9MHz/20mW出力 30 | unsigned const char pair_id[8] = {0x00 , 0x1D , 0x12 , 0x91 , 0x00 , 0x00 , 0x05 , 0xA7}; // 接続先MACアドレス 31 | unsigned const char mac_adr[16] = {0xFE , 0x80 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x02 , 0x1D , 0x12 , 0x91 , 0x00 , 0x00 , 0x05 , 0xE7}; // 接続先IPv6アドレス 32 | unsigned const char my_port[2] = { 0x01 , 0x23 }; // オープンするUDPポート 33 | unsigned const char dist_port[2] = { 0x0E , 0x1A }; // 送信先UDPポート 34 | unsigned const char password[16] = { '1' , '1' , '1' , '1' , '2', '2' , '2' , '2' , '3' , '3' , '3' , '3' , '4' , '4' , '4' , '4' }; // PANA認証時のパスワード 35 | unsigned const char radiodata[4] = { 'T' , 'E' , 'S' , 'T' }; // 送信データ 36 | 37 | CMD_FORMAT cmd_format; 38 | 39 | BP35C0J11::BP35C0J11(void) 40 | { 41 | 42 | } 43 | 44 | /******************************************************************************** 45 | * Name : j11_init 46 | * Function : initial setting bp35c0-j11 47 | * input : - 48 | * return : - 49 | *********************************************************************************/ 50 | void BP35C0J11::j11_init(void) { 51 | 52 | // configure output D20/D21 53 | pinMode(PIN_ENABLE, OUTPUT); 54 | pinMode(PIN_RESET, OUTPUT); 55 | digitalWrite(PIN_ENABLE, HIGH); 56 | 57 | 58 | delay(1000); 59 | 60 | // Serial port initial 61 | Serial2.begin(115200); 62 | Serial.begin(115200); 63 | Serial.write("RESET"); 64 | Serial.println(""); 65 | 66 | digitalWrite(PIN_RESET, LOW); // reset 67 | delay(500); 68 | digitalWrite(PIN_RESET, HIGH); 69 | 70 | } 71 | 72 | /******************************************************************************** 73 | * Name : wait_msg 74 | * Function : wait for response from bp35c0-j11 75 | * input : - 76 | * return : TRUE/FALSE 77 | *********************************************************************************/ 78 | boolean BP35C0J11::wait_msg(void) 79 | { 80 | unsigned long start_time; 81 | unsigned long current_time; 82 | unsigned char rcvdata[128] = {0} ; 83 | unsigned char cnt = 0 ; 84 | start_time = millis(); 85 | while (Serial2.available() == 0) 86 | { 87 | current_time = millis(); 88 | if ((current_time - start_time) > TIMEOUT) { 89 | Serial.println("receive timeout"); 90 | return FALSE; 91 | } 92 | 93 | } 94 | while (Serial2.available() > 0 ) { 95 | delay(5); 96 | rcvdata[cnt] = Serial2.read(); 97 | #ifdef DEBUG 98 | Serial.print(rcvdata[cnt] , HEX); 99 | #endif 100 | cnt++; 101 | if (cnt >= 128) { 102 | Serial.println("receive data over flow"); 103 | return FALSE; 104 | } 105 | } 106 | if (rcvdata[0] == uni_res[0] && rcvdata[1] == uni_res[1] && 107 | rcvdata[2] == uni_res[2] && rcvdata[3] == uni_res[3]) { // RESPONSE/NORTIFICATION 108 | switch (rcvdata[4] << 8 | rcvdata[5]) { 109 | case (NORT_WAKE): 110 | 111 | break; 112 | case (RES_INI): 113 | if (rcvdata[12] == 0x01) { 114 | Serial.println("Init Success"); 115 | } else { 116 | Serial.println("Init Error"); 117 | return FALSE; 118 | } 119 | break; 120 | case (RES_PANA_SET): 121 | if (rcvdata[12] == 0x01) { 122 | Serial.println("PANA Password set Success"); 123 | } else { 124 | Serial.println("PANA Password set Error"); 125 | return FALSE; 126 | } 127 | break; 128 | case (RES_SCAN): 129 | 130 | break; 131 | case (NORT_SCAN): 132 | break; 133 | case (RES_HAN): 134 | if (rcvdata[12] == 0x01) { 135 | Serial.println("HAN Act Success"); 136 | } else { 137 | Serial.println("HAN Act Error"); 138 | return FALSE; 139 | } 140 | break; 141 | case (RES_PANA): 142 | if (rcvdata[12] == 0x01) { 143 | Serial.println("PANA Act Success"); 144 | } else { 145 | Serial.println("PANA Act Error"); 146 | return FALSE; 147 | } 148 | break; 149 | case (NORT_PANA): 150 | if (rcvdata[12] == 0x01) { 151 | Serial.println("PANA Connect Success"); 152 | } else { 153 | Serial.println("PANA Connecgt Error"); 154 | return FALSE; 155 | } 156 | break; 157 | case (RES_CON_SET): 158 | if (rcvdata[12] == 0x01) { 159 | Serial.println("Normal connect mode"); 160 | } else { 161 | Serial.println("connect mode change error"); 162 | return FALSE; 163 | } 164 | break; 165 | case (RES_PORTOPEN): 166 | if (rcvdata[12] == 0x01) { 167 | Serial.println("UDP port open Success"); 168 | } else { 169 | Serial.println("UDP port open Error"); 170 | return FALSE; 171 | } 172 | break; 173 | case (RES_UDPSEND): 174 | if (rcvdata[12] == 0x01) { 175 | Serial.println("UDP send Success"); 176 | } else { 177 | Serial.println("UDP send Error"); 178 | return FALSE; 179 | } 180 | break; 181 | case (0x2FFF): 182 | Serial.println("checksum error"); 183 | return FALSE; 184 | break; 185 | default: 186 | Serial.println("uni code error"); 187 | return FALSE; 188 | break; 189 | } 190 | 191 | } else { 192 | Serial.println("recv data error"); 193 | return FALSE; 194 | } 195 | 196 | return TRUE; 197 | } 198 | 199 | 200 | 201 | /******************************************************************************** 202 | * Name : cmd_send 203 | * Function : REQUEST command to bp35c0-j11 204 | * input : cmd - REQUEST command 205 | * return : TRUE/FALSE 206 | *********************************************************************************/ 207 | boolean BP35C0J11::cmd_send(unsigned short cmd) { 208 | unsigned short hdr_chksum = uni_req[0] + uni_req[1] + uni_req[2] + uni_req[3] ; 209 | unsigned short dat_chksum = 0 ; 210 | unsigned short msg_length = 0 ; 211 | unsigned short dat_length = 0 ; 212 | unsigned short send_dat_size = 0 ; 213 | unsigned char data[128] = {0}; 214 | 215 | unsigned char send_data[128] = {0} ; 216 | unsigned char cnt = 0 ; 217 | 218 | switch (cmd) { 219 | case (CMD_RESET): 220 | dat_length = 0; 221 | msg_length = (unsigned short)(4 + dat_length); 222 | hdr_chksum += CMD_RESET + msg_length; 223 | dat_chksum = 0 ; 224 | msg_create(CMD_RESET , msg_length , hdr_chksum , dat_chksum, data , send_data ); 225 | Serial2.write(send_data, (msg_length + CMD_HDR_LEN)); 226 | #ifdef DEBUG 227 | debugmsg( msg_length + CMD_HDR_LEN , send_data); 228 | #endif 229 | 230 | break; 231 | case (CMD_INI): 232 | dat_length = (unsigned short)4; 233 | msg_length = (unsigned short )( 4 + dat_length); 234 | hdr_chksum += CMD_INI + msg_length ; 235 | for (cnt = 0 ; cnt < dat_length ; cnt++ ) { 236 | data[cnt] = ini_data[cnt] ; 237 | } 238 | for (cnt = 0 ; cnt < dat_length ; cnt++) { 239 | dat_chksum += data[cnt]; 240 | } 241 | msg_create(CMD_INI , msg_length , hdr_chksum , dat_chksum, data , send_data ); 242 | Serial2.write(send_data, (msg_length + CMD_HDR_LEN)); 243 | #ifdef DEBUG 244 | debugmsg( msg_length + CMD_HDR_LEN , send_data); 245 | #endif 246 | break; 247 | case (CMD_PANA_SET): 248 | dat_length = (unsigned short)16 ; 249 | msg_length = (unsigned short)(4 + dat_length); 250 | hdr_chksum += CMD_PANA_SET + msg_length; 251 | for (cnt = 0 ; cnt < dat_length ; cnt++ ) { 252 | data[cnt] = password[cnt] ; 253 | } 254 | for (cnt = 0 ; cnt < dat_length ; cnt++) { 255 | dat_chksum += data[cnt]; 256 | } 257 | msg_create(CMD_PANA_SET , msg_length , hdr_chksum , dat_chksum, data , send_data ); 258 | Serial2.write(send_data, (msg_length + CMD_HDR_LEN)); 259 | #ifdef DEBUG 260 | debugmsg( msg_length + CMD_HDR_LEN , send_data); 261 | #endif 262 | 263 | break; 264 | case (CMD_SCAN): 265 | break; 266 | case (CMD_HAN): 267 | dat_length = (unsigned short)8 ; 268 | msg_length = (unsigned short)(4 + dat_length); 269 | hdr_chksum += CMD_HAN + msg_length; 270 | for (cnt = 0 ; cnt < dat_length ; cnt++ ) { 271 | data[cnt] = pair_id[cnt] ; 272 | } 273 | for (cnt = 0 ; cnt < dat_length ; cnt++) { 274 | dat_chksum += data[cnt]; 275 | } 276 | msg_create(CMD_HAN , msg_length , hdr_chksum , dat_chksum, data , send_data ); 277 | Serial2.write(send_data, (msg_length + CMD_HDR_LEN)); 278 | #ifdef DEBUG 279 | debugmsg( msg_length + CMD_HDR_LEN , send_data); 280 | #endif 281 | 282 | 283 | break; 284 | case (CMD_PANA): 285 | dat_length = 0; 286 | msg_length = (unsigned short)(4 + dat_length); 287 | hdr_chksum += CMD_PANA + msg_length; 288 | dat_chksum = 0 ; 289 | msg_create(CMD_PANA , msg_length , hdr_chksum , dat_chksum, data , send_data ); 290 | Serial2.write(send_data, msg_length + CMD_HDR_LEN); 291 | #ifdef DEBUG 292 | debugmsg( msg_length + CMD_HDR_LEN , send_data); 293 | #endif 294 | break; 295 | case (CMD_CON_SET): 296 | dat_length = 1; 297 | msg_length = (unsigned short)(4 + dat_length); 298 | hdr_chksum += CMD_CON_SET + msg_length; 299 | data[0] = 0x02 ; 300 | dat_chksum = data[0] ; 301 | msg_create(CMD_CON_SET , msg_length , hdr_chksum , dat_chksum, data , send_data ); 302 | Serial2.write(send_data, msg_length + CMD_HDR_LEN); 303 | #ifdef DEBUG 304 | debugmsg( msg_length + CMD_HDR_LEN , send_data); 305 | #endif 306 | 307 | break; 308 | case (CMD_PORTOPEN): 309 | dat_length = 2; 310 | msg_length = (unsigned short)(4 + dat_length); 311 | hdr_chksum += CMD_PORTOPEN + msg_length; 312 | for (cnt = 0 ; cnt < dat_length ; cnt++ ) { 313 | data[cnt] = my_port[cnt] ; 314 | } 315 | for (cnt = 0 ; cnt < dat_length ; cnt++) { 316 | dat_chksum += data[cnt]; 317 | } 318 | msg_create(CMD_PORTOPEN , msg_length , hdr_chksum , dat_chksum, data , send_data ); 319 | Serial2.write(send_data, msg_length + CMD_HDR_LEN); 320 | #ifdef DEBUG 321 | debugmsg( msg_length + CMD_HDR_LEN , send_data); 322 | #endif 323 | break; 324 | case (CMD_UDPSEND): 325 | send_dat_size = 4 ; 326 | dat_length = 22 + send_dat_size ; 327 | msg_length = (unsigned short)(4 + dat_length); 328 | hdr_chksum += CMD_UDPSEND + msg_length; 329 | for (cnt = 0 ; cnt < 16 ; cnt++ ) { 330 | data[cnt] = mac_adr[cnt] ; 331 | } 332 | data[16] = my_port[0] ; 333 | data[17] = my_port[1] ; // 送信元UDPポート :0x0123 334 | data[18] = dist_port[0] ; 335 | data[19] = dist_port[1] ; // 送信先UDPポート:0x0E1A 336 | data[20] = (unsigned char)(send_dat_size >> 8); 337 | data[21] = (unsigned char)(send_dat_size & 0xFF); // send data length 338 | for (cnt = 0 ; cnt < send_dat_size ; cnt++) { 339 | data[22 + cnt] = radiodata[cnt]; // data 340 | } 341 | for (cnt = 0 ; cnt < dat_length ; cnt++) { 342 | dat_chksum += data[cnt]; 343 | } 344 | msg_create(CMD_UDPSEND , msg_length , hdr_chksum , dat_chksum, data , send_data ); 345 | Serial2.write(send_data, msg_length + CMD_HDR_LEN); 346 | #ifdef DEBUG 347 | debugmsg( msg_length + CMD_HDR_LEN , send_data); 348 | #endif 349 | break; 350 | default: 351 | 352 | break; 353 | } 354 | 355 | return TRUE; 356 | } 357 | 358 | /******************************************************************************** 359 | * Name : msg_create 360 | * Function : create Request command format 361 | * input : cmd - Request command 362 | * msg_length - message data length 363 | * hdr_chksum - header checksum 364 | dat_chksum - data checksum 365 | *pdada - wireless data 366 | *psend_data- request command format data 367 | * return : - 368 | *********************************************************************************/ 369 | void static BP35C0J11::msg_create(unsigned short cmd , unsigned short msg_length , unsigned short hdr_chksum , unsigned short dat_chksum, unsigned char *pdata , unsigned char *psend_data ) 370 | { 371 | unsigned char cnt = 0 ; 372 | 373 | for (cnt = 0 ; cnt < 4 ; cnt++) { 374 | psend_data[cnt] = uni_req[cnt]; 375 | } 376 | psend_data[4] = (unsigned char)((cmd & 0xFF00) >> 8); 377 | psend_data[5] = (unsigned char)(cmd & 0xFF); 378 | psend_data[6] = (unsigned char)((msg_length & 0xFF00) >> 8); 379 | psend_data[7] = (unsigned char)(msg_length & 0xFF); 380 | psend_data[8] = (unsigned char)((hdr_chksum & 0xFF00) >> 8); 381 | psend_data[9] = (unsigned char)(hdr_chksum & 0xFF); 382 | psend_data[10] = (unsigned char)((dat_chksum & 0xFF00) >> 8); 383 | psend_data[11] = (unsigned char)(dat_chksum & 0xFF); 384 | 385 | if (msg_length > 4) { 386 | for (cnt = 0 ; cnt < msg_length - 4 ; cnt++) 387 | { 388 | psend_data[12 + cnt] = pdata[cnt]; 389 | } 390 | } 391 | } 392 | 393 | 394 | 395 | /******************************************************************************** 396 | * Name : debugmsg 397 | * Function : output serial console for debug 398 | * input : datalength - output data lengh 399 | psend_data - output data pointer 400 | * return : - 401 | *********************************************************************************/ 402 | void BP35C0J11::debugmsg(unsigned short datalength , unsigned char* psend_data) { 403 | unsigned char cnt = 0 ; 404 | 405 | for ( cnt = 0 ; cnt < datalength ; cnt++) { 406 | Serial.print(psend_data[cnt] , HEX); 407 | Serial.print(" "); 408 | } 409 | Serial.println(""); 410 | } 411 | 412 | 413 | 414 | -------------------------------------------------------------------------------- /SPRESENSE-WISUN-EVK-701/bp35c0-j11.h: -------------------------------------------------------------------------------- 1 | /* 2 | bp35c0-j11.h 3 | Copyright (c) 2019 ROHM Co.,Ltd. 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. 22 | */ 23 | #ifndef _BP35C0J11_H_ 24 | #define _BP35C0J11_H_ 25 | 26 | #define DEBUG 27 | 28 | 29 | #define CMD_HDR_LEN ((unsigned char)8) 30 | #define UNI_CODE_LEN ((unsigned char)4) 31 | 32 | #define CMD_RESET (0x00D9) 33 | #define CMD_INI (0x005F) 34 | #define CMD_HAN (0x000A) 35 | #define CMD_PANA (0x003A) 36 | #define CMD_PANA_SET (0x002C) 37 | #define CMD_CON_SET (0x0025) 38 | #define CMD_UDPSEND (0x0008) 39 | #define CMD_SCAN (0x0051) 40 | #define CMD_PORTOPEN (0x0005) 41 | 42 | #define NORT_WAKE (0x6019) 43 | #define RES_INI (0x205F) 44 | #define RES_HAN (0x200A) 45 | #define RES_PANA (0x203A) 46 | #define RES_PANA_SET (0x202C) 47 | #define RES_CON_SET (0x2025) 48 | #define RES_UDPSEND (0x2008) 49 | #define RES_SCAN (0x2051) 50 | #define NORT_SCAN (0x4051) 51 | #define RES_PORTOPEN (0x2005) 52 | #define NORT_PANA (0x6028) 53 | 54 | #define TIMEOUT ((unsigned short)10000) 55 | 56 | #define PIN_ENABLE (PIN_D20) // level shifter enable pin 57 | #define PIN_RESET (PIN_D21) // wisun module reset pin 58 | 59 | #define TRUE 1 60 | #define FALSE 0 61 | 62 | typedef struct { 63 | unsigned char uni_code[4]; 64 | unsigned char cmd_code[2]; 65 | unsigned char msg_len[2]; 66 | unsigned char hdr_chksum[2]; 67 | unsigned char dat_chksum[2]; 68 | unsigned char data[128]; 69 | }CMD_FORMAT; 70 | 71 | class BP35C0J11 72 | { 73 | public: 74 | BP35C0J11(void); 75 | void j11_init(void); 76 | boolean wait_msg(void); 77 | boolean cmd_send(unsigned short cmd); 78 | void static msg_create(unsigned short cmd , unsigned short msg_length ,unsigned short hdr_chksum , unsigned short dat_chksum, unsigned char *pdata , unsigned char *psend_data ); 79 | private: 80 | void static debugmsg(unsigned short datalength , unsigned char *psend_data); 81 | }; 82 | #endif //_BP35C0J11_H_ 83 | 84 | -------------------------------------------------------------------------------- /SPRESENSE-WISUN-EVK-701/documents/BP35C0-J11(Wi-SUN Enhanced HAN)/J11_UART_IFコマンド仕様書_第1.1版.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RohmSemiconductor/Arduino/447c576a4ff34215adaf2ae0e5ea68fbc4d73b8f/SPRESENSE-WISUN-EVK-701/documents/BP35C0-J11(Wi-SUN Enhanced HAN)/J11_UART_IFコマンド仕様書_第1.1版.pdf -------------------------------------------------------------------------------- /SPRESENSE-WISUN-EVK-701/documents/BP35C2(USB dongle)/BP35C0_BP35C2-command_reference-dse-j.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RohmSemiconductor/Arduino/447c576a4ff34215adaf2ae0e5ea68fbc4d73b8f/SPRESENSE-WISUN-EVK-701/documents/BP35C2(USB dongle)/BP35C0_BP35C2-command_reference-dse-j.pdf -------------------------------------------------------------------------------- /SPRESENSE-WISUN-EVK-701/documents/SPRESENSE-WiSUN-EVK-701_サンプルソフトウェア説明書_ROHC.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RohmSemiconductor/Arduino/447c576a4ff34215adaf2ae0e5ea68fbc4d73b8f/SPRESENSE-WISUN-EVK-701/documents/SPRESENSE-WiSUN-EVK-701_サンプルソフトウェア説明書_ROHC.pdf -------------------------------------------------------------------------------- /SPRESENSE-WISUN-EVK-701/examples/SPRESENSE-WISUN-EVK-701/SPRESENSE-WISUN-EVK-701.ino: -------------------------------------------------------------------------------- 1 | /* 2 | SPRESENSE-WISUN-EVK-701 3 | Copyright (c) 2019 ROHM Co.,Ltd. 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. 22 | */ 23 | #include "bp35c0-j11.h" 24 | 25 | 26 | unsigned char state = 0 ; 27 | 28 | BP35C0J11 bp35c0j11; 29 | 30 | void setup() { 31 | boolean rc = FALSE ; 32 | bp35c0j11.j11_init(); 33 | rc = bp35c0j11.wait_msg(); 34 | if(rc == TRUE){ 35 | state = 1 ; // hardware reset end 36 | }else{ 37 | state = 0 ; 38 | } 39 | 40 | 41 | } 42 | 43 | void loop() { 44 | 45 | unsigned char msg_length = 0 ; 46 | boolean rc = 0 ; 47 | 48 | #ifdef DEBUG 49 | Serial.print("State = "); 50 | Serial.println(state, DEC); 51 | #endif 52 | 53 | delay(500); 54 | switch (state) { 55 | case(0): // need hardware reset 56 | rc = bp35c0j11.cmd_send(CMD_RESET); 57 | rc = bp35c0j11.wait_msg(); 58 | if(rc == TRUE){ 59 | state = 1 ; 60 | } 61 | break; 62 | case(1): // init state 63 | rc = bp35c0j11.cmd_send(CMD_INI); 64 | rc = bp35c0j11.wait_msg(); 65 | if(rc == TRUE){ 66 | state = 2; 67 | } 68 | break; 69 | case(2): // HAN PANA setting 70 | rc = bp35c0j11.cmd_send(CMD_PANA_SET); 71 | rc = bp35c0j11.wait_msg(); 72 | if(rc == TRUE){ 73 | state = 4; 74 | } 75 | break; 76 | case(3): // active scan 77 | rc = bp35c0j11.cmd_send(CMD_SCAN); 78 | rc = bp35c0j11.wait_msg(); 79 | if(rc == TRUE){ 80 | rc = bp35c0j11.wait_msg(); 81 | if(rc == TRUE){ 82 | state = 4; 83 | } 84 | } 85 | break; 86 | case(4): // HAN act 87 | rc = bp35c0j11.cmd_send(CMD_HAN); 88 | rc = bp35c0j11.wait_msg(); 89 | if(rc == TRUE){ 90 | state = 5; 91 | } 92 | break; 93 | case(5): // HAN PANA act 94 | rc = bp35c0j11.cmd_send(CMD_PANA); 95 | rc = bp35c0j11.wait_msg(); 96 | if(rc == TRUE){ 97 | rc = bp35c0j11.wait_msg(); 98 | if(rc == TRUE){ 99 | state = 7; 100 | } 101 | } 102 | break; 103 | case(6): // rcv mode change 104 | rc = bp35c0j11.cmd_send(CMD_CON_SET); 105 | rc = bp35c0j11.wait_msg(); 106 | if(rc == TRUE){ 107 | state = 7; 108 | } 109 | break; 110 | case(7): // my_port open 111 | rc = bp35c0j11.cmd_send(CMD_PORTOPEN); 112 | rc = bp35c0j11.wait_msg(); 113 | if(rc == TRUE){ 114 | state = 8; 115 | } 116 | break; 117 | case(8): // UDP send 118 | rc = bp35c0j11.cmd_send(CMD_UDPSEND); 119 | rc = bp35c0j11.wait_msg(); 120 | if(rc == TRUE){ 121 | delay(5000); 122 | } 123 | break; 124 | default: // error 125 | state = 0 ; 126 | break; 127 | 128 | } 129 | 130 | 131 | 132 | 133 | } 134 | 135 | -------------------------------------------------------------------------------- /SPRESENSE-WISUN-EVK-701/keywords.txt: -------------------------------------------------------------------------------- 1 | BP35C0J11 KEYWORD1 2 | j11_init KEYWORD2 3 | wait_msg KEYWORD2 4 | cmd_send KEYWORD2 5 | msg_create KEYWORD2 6 | debugmsg KEYWORD2 7 | -------------------------------------------------------------------------------- /Sensors-Add-on-Demo/Sensors-Add-on-Demo.ino: -------------------------------------------------------------------------------- 1 | /***************************************************************************** 2 | Sensors-Add-on-Demo.ino 3 | Copyright (c) 2018 ROHM Co.,Ltd. 4 | Permission is hereby granted, free of charge, to any person obtaining a copy 5 | of this software and associated documentation files (the "Software"), to deal 6 | in the Software without restriction, including without limitation the rights 7 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 8 | copies of the Software, and to permit persons to whom the Software is 9 | furnished to do so, subject to the following conditions: 10 | The above copyright notice and this permission notice shall be included in 11 | all copies or substantial portions of the Software. 12 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 13 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 14 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 15 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 16 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 17 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 18 | THE SOFTWARE. 19 | ******************************************************************************/ 20 | #include 21 | #include 22 | #include 23 | #include 24 | #include 25 | 26 | KX122 kx122(KX122_DEVICE_ADDRESS_1F); 27 | KX126 kx126(KX126_DEVICE_ADDRESS_1F); 28 | BM1422AGMV bm1422agmv(BM1422AGMV_DEVICE_ADDRESS_0F); 29 | BM1383AGLV bm1383aglv; 30 | bool KX122_found = false; 31 | bool KX126_found = false; 32 | 33 | void setup() { 34 | byte rc; 35 | 36 | 37 | Serial.begin(115200); 38 | while (!Serial); 39 | 40 | Wire.begin(); 41 | 42 | rc = kx122.init(); 43 | if (rc != 0) { 44 | Serial.flush(); 45 | }else{ 46 | KX122_found = true; 47 | } 48 | 49 | rc = kx126.init(); 50 | if (rc != 0) { 51 | Serial.flush(); 52 | }else{ 53 | KX126_found = true; 54 | } 55 | 56 | if(!KX122_found && !KX126_found){ 57 | Serial.println(F("KX122/KX126 initialization failed")); 58 | } 59 | 60 | rc = bm1422agmv.init(); 61 | if (rc != 0) { 62 | Serial.println(F("BM1422AGMV initialization failed")); 63 | Serial.flush(); 64 | } 65 | 66 | rc = bm1383aglv.init(); 67 | if (rc != 0) { 68 | Serial.println("BM1383AGLV initialization failed"); 69 | Serial.flush(); 70 | } 71 | 72 | } 73 | 74 | void loop() { 75 | byte rc; 76 | float acc[3], mag[3], press = 0, temp = 0; 77 | 78 | if(KX122_found){ 79 | rc = kx122.get_val(acc); 80 | if (rc == 0) { 81 | Serial.write("KX122 (X) = "); 82 | Serial.print(acc[0]); 83 | Serial.println(" [g]"); 84 | Serial.write("KX122 (Y) = "); 85 | Serial.print(acc[1]); 86 | Serial.println(" [g]"); 87 | Serial.write("KX122 (Z) = "); 88 | Serial.print(acc[2]); 89 | Serial.println(" [g]"); 90 | } 91 | } 92 | 93 | if(KX126_found){ 94 | rc = kx126.get_val(acc); 95 | if (rc == 0) { 96 | Serial.write("KX126 (X) = "); 97 | Serial.print(acc[0]); 98 | Serial.println(" [g]"); 99 | Serial.write("KX126 (Y) = "); 100 | Serial.print(acc[1]); 101 | Serial.println(" [g]"); 102 | Serial.write("KX126 (Z) = "); 103 | Serial.print(acc[2]); 104 | Serial.println(" [g]"); 105 | } 106 | } 107 | 108 | rc = bm1422agmv.get_val(mag); 109 | 110 | if (rc == 0) { 111 | Serial.print("BM1422AGMV XDATA="); 112 | Serial.print(mag[0], 3); 113 | Serial.println("[uT]"); 114 | Serial.print("BM1422AGMV YDATA="); 115 | Serial.print(mag[1], 3); 116 | Serial.println("[uT]"); 117 | Serial.print("BM1422AGMV ZDATA="); 118 | Serial.print(mag[2], 3); 119 | Serial.println("[uT]"); 120 | } 121 | 122 | rc = bm1383aglv.get_val(&press, &temp); 123 | if (rc == 0) { 124 | Serial.print("BM1383AGLV (PRESS) = "); 125 | Serial.print(press); 126 | Serial.println(" [hPa]"); 127 | Serial.print("BM1383AGLV (TEMP) = "); 128 | Serial.print(temp); 129 | Serial.println(" [degrees Celsius]"); 130 | Serial.println(); 131 | } 132 | 133 | delay(500); 134 | 135 | } 136 | -------------------------------------------------------------------------------- /images/add_library.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RohmSemiconductor/Arduino/447c576a4ff34215adaf2ae0e5ea68fbc4d73b8f/images/add_library.PNG -------------------------------------------------------------------------------- /images/arduino_ide.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RohmSemiconductor/Arduino/447c576a4ff34215adaf2ae0e5ea68fbc4d73b8f/images/arduino_ide.png -------------------------------------------------------------------------------- /images/ble_pins2.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RohmSemiconductor/Arduino/447c576a4ff34215adaf2ae0e5ea68fbc4d73b8f/images/ble_pins2.jpg -------------------------------------------------------------------------------- /images/sens_pins2.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RohmSemiconductor/Arduino/447c576a4ff34215adaf2ae0e5ea68fbc4d73b8f/images/sens_pins2.jpg -------------------------------------------------------------------------------- /images/serial_monitor.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RohmSemiconductor/Arduino/447c576a4ff34215adaf2ae0e5ea68fbc4d73b8f/images/serial_monitor.png -------------------------------------------------------------------------------- /images/sketch_folder.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RohmSemiconductor/Arduino/447c576a4ff34215adaf2ae0e5ea68fbc4d73b8f/images/sketch_folder.png -------------------------------------------------------------------------------- /kx13x/examples/KX13X/kx13x.ino: -------------------------------------------------------------------------------- 1 | /* 2 | The MIT License (MIT) 3 | Copyright (c) 2020 ROHM Co.,Ltd. 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a 6 | copy of this software and associated documentation files (the 7 | "Software"), to deal in the Software without restriction, including 8 | without limitation the rights to use, copy, modify, merge, publish, 9 | distribute, sublicense, and/or sell copies of the Software, and to 10 | permit persons to whom the Software is furnished to do so, subject to 11 | the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included 14 | in all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 17 | OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 18 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 19 | IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY 20 | CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 21 | TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 22 | SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 23 | */ 24 | 25 | #include 26 | #include 27 | 28 | #include "platform.h" 29 | #include "kx13x.h" 30 | #include "kx13x_example.h" 31 | 32 | #define UNUSED_VAR(a) (void)a 33 | 34 | /* Set sensor example configuration, modify example config in kx13x_example.c */ 35 | uint8_t example_config = KX13X_EXAMPLE_ADP_DATA; 36 | /* Set sensor I2C address */ 37 | uint8_t sensor_sad = KX13X_I2C_ADDRESS_1F; 38 | 39 | /* Set Arduino int pins connected to sensor int1/2 */ 40 | #define ARDUINO_INT1_PIN 5 41 | #define ARDUINO_INT2_PIN 6 42 | 43 | /* Arduino loop poll delay */ 44 | #define ARDUINO_POLL_DELAY_MS 10 45 | 46 | /* Sensor driver data and pointer to sensor config */ 47 | struct kx13x sensor_dev; 48 | struct kx13x_cfg *sensor_cfg; 49 | /* Arduino platform functions needed by driver */ 50 | struct platform arduino_plat; 51 | /* Flag to indicate timer poll or interrupt */ 52 | uint8_t timer_poll; 53 | 54 | /* Arduino platform functions */ 55 | int arduino_debug_print(struct platform *plat, char *str) 56 | { 57 | UNUSED_VAR(plat); 58 | Serial.print(str); 59 | return PLAT_RC_OK; 60 | } 61 | 62 | int arduino_i2c_write(struct platform *plat, uint8_t reg, uint8_t *data, uint8_t size) 63 | { 64 | uint8_t rc; 65 | uint8_t sad = *(uint8_t*)plat->plat_data; 66 | 67 | Wire.beginTransmission(sad); 68 | Wire.write(reg); 69 | Wire.write(data, size); 70 | rc = Wire.endTransmission(true); 71 | 72 | if (rc != 0) { 73 | return PLAT_RC_FAIL; 74 | } 75 | 76 | return PLAT_RC_OK; 77 | } 78 | 79 | int arduino_i2c_read(struct platform *plat, uint8_t reg, uint8_t *data, uint8_t size) 80 | { 81 | uint8_t rc; 82 | uint8_t cnt; 83 | uint8_t sad = *(uint8_t*)plat->plat_data; 84 | 85 | Wire.beginTransmission(sad); 86 | Wire.write(reg); 87 | rc = Wire.endTransmission(false); 88 | if (rc != 0) { 89 | Serial.print("Read failed!\n"); 90 | return PLAT_RC_FAIL; 91 | } 92 | 93 | Wire.requestFrom((int)sad, (int)size, (int)true); 94 | cnt = 0; 95 | while (Wire.available()) { 96 | data[cnt] = Wire.read(); 97 | cnt++; 98 | } 99 | 100 | return PLAT_RC_OK; 101 | } 102 | 103 | int arduino_spi_write(struct platform *plat, uint8_t reg, uint8_t *data, uint8_t size) 104 | { 105 | UNUSED_VAR(plat); 106 | UNUSED_VAR(reg); 107 | UNUSED_VAR(data); 108 | UNUSED_VAR(size); 109 | // TODO: Add SPI write 110 | return PLAT_RC_FAIL; 111 | } 112 | 113 | int arduino_spi_read(struct platform *plat, uint8_t reg, uint8_t *data, uint8_t size) 114 | { 115 | UNUSED_VAR(plat); 116 | UNUSED_VAR(reg); 117 | UNUSED_VAR(data); 118 | UNUSED_VAR(size); 119 | // TODO: Add SPI read 120 | return PLAT_RC_FAIL; 121 | } 122 | 123 | int arduino_delay_ms(struct platform *plat, uint16_t ms) 124 | { 125 | UNUSED_VAR(plat); 126 | delay(ms); 127 | return PLAT_RC_OK; 128 | } 129 | 130 | int init_sensor_dev(struct kx13x *dev) 131 | { 132 | int rc; 133 | char *sensor_name; 134 | 135 | /* Pass pointer to sad as private plat data */ 136 | arduino_plat.plat_data = (void*)&sensor_sad; 137 | /* Pass platform functions */ 138 | arduino_plat.write = arduino_i2c_write; 139 | arduino_plat.read = arduino_i2c_read; 140 | //arduino_plat.write = arduino_spi_write; 141 | //arduino_plat.read = arduino_spi_read; 142 | arduino_plat.delay_ms = arduino_delay_ms; 143 | arduino_plat.debug_print = arduino_debug_print; 144 | 145 | rc = kx13x_init(dev, &arduino_plat); 146 | if (rc != KX13X_RC_OK) { 147 | Serial.print("kx13x_init fail\n"); 148 | return rc; 149 | } 150 | 151 | sensor_name = kx13x_get_name(dev); 152 | if (sensor_name == NULL) { 153 | Serial.print("kx13x_get_name fail\n"); 154 | return KX13X_RC_ERR; 155 | } 156 | 157 | Serial.print("init_sensor_dev ok, sensor type: "); 158 | Serial.println(sensor_name); 159 | 160 | return KX13X_RC_OK; 161 | } 162 | 163 | /* Flags to indicate if isr called */ 164 | uint8_t int1_isr_called = 0; 165 | uint8_t int2_isr_called = 0; 166 | 167 | void int1_isr(void) 168 | { 169 | int1_isr_called = 1; 170 | } 171 | 172 | void int_pin2_isr(void) 173 | { 174 | int2_isr_called = 1; 175 | } 176 | 177 | int config_host_int1_pin(uint8_t int1_pin, uint8_t mode, uint8_t trigger) 178 | { 179 | pinMode(int1_pin, mode); 180 | attachInterrupt(digitalPinToInterrupt(int1_pin), int1_isr, trigger); 181 | return 0; 182 | } 183 | 184 | int config_host_int2_pin(uint8_t int2_pin, uint8_t mode, uint8_t trigger) 185 | { 186 | pinMode(int2_pin, mode); 187 | attachInterrupt(digitalPinToInterrupt(int2_pin), int_pin2_isr, trigger); 188 | return 0; 189 | } 190 | 191 | /* Arduino setup */ 192 | void setup() { 193 | int rc; 194 | 195 | Serial.begin(115200); 196 | while (!Serial); 197 | Wire.begin(); 198 | 199 | timer_poll = 1; 200 | 201 | /* init sensor driver */ 202 | rc = init_sensor_dev(&sensor_dev); 203 | if (rc != KX13X_RC_OK) { 204 | Serial.print("init_sensor_dev fail\n"); 205 | return; 206 | } 207 | 208 | sensor_cfg = kx13x_example_update_config(&sensor_dev, example_config); 209 | 210 | /* config host int pins based on sensor config */ 211 | if (sensor_cfg->int1) { 212 | timer_poll = 0; 213 | if (sensor_cfg->int1->level == KX13X_INT_LEVEL_HIGH) { 214 | config_host_int1_pin(ARDUINO_INT1_PIN, INPUT, RISING); 215 | } else { 216 | config_host_int1_pin(ARDUINO_INT1_PIN, INPUT, FALLING); 217 | } 218 | 219 | } 220 | 221 | if (sensor_cfg->int2) { 222 | timer_poll = 0; 223 | if (sensor_cfg->int2->level == KX13X_INT_LEVEL_HIGH) { 224 | config_host_int2_pin(ARDUINO_INT2_PIN, INPUT, RISING); 225 | } else { 226 | config_host_int2_pin(ARDUINO_INT2_PIN, INPUT, FALLING); 227 | } 228 | 229 | } 230 | 231 | /* set sensor to operating mode */ 232 | rc = kx13x_set_oper_mode(&sensor_dev, KX13X_OPER_MODE_OPERATING); 233 | if (rc != KX13X_RC_OK) { 234 | Serial.println("fail to set operating mode"); 235 | return; 236 | } 237 | 238 | delay(1000); 239 | Serial.println(" "); 240 | } 241 | 242 | void loop_interrupt() 243 | { 244 | uint8_t int1_occured = 0; 245 | uint8_t int2_occured = 0; 246 | 247 | if (int1_isr_called) { 248 | int1_occured = 1; 249 | int1_isr_called = 0; 250 | } 251 | 252 | if (int2_isr_called) { 253 | int2_occured = 1; 254 | int2_isr_called = 0; 255 | } 256 | 257 | if (int1_occured || int2_occured) { 258 | (void)kx13x_example_handle_interrupt(&sensor_dev); 259 | } 260 | } 261 | 262 | void loop_timer() 263 | { 264 | 265 | (void)kx13x_example_poll_interrupt(&sensor_dev); 266 | } 267 | 268 | /* Arduino loop */ 269 | void loop() { 270 | 271 | delay(ARDUINO_POLL_DELAY_MS); 272 | 273 | if (timer_poll) { 274 | loop_timer(); 275 | } else { 276 | loop_interrupt(); 277 | } 278 | } 279 | -------------------------------------------------------------------------------- /kx13x/keywords.txt: -------------------------------------------------------------------------------- 1 | kx13x_init KEYWORD2 2 | kx13x_get_name KEYWORD2 3 | kx13x_set_config KEYWORD2 4 | kx13x_debug_dump_regs KEYWORD2 5 | kx13x_reset KEYWORD2 6 | kx13x_release_int KEYWORD2 7 | kx13x_get_int_ins123 KEYWORD2 8 | kx13x_get_int_status KEYWORD2 9 | kx13x_set_int_cfg KEYWORD2 10 | kx13x_interrupt_cfg KEYWORD2 11 | kx13x_set_int_enabled KEYWORD2 12 | kx13x_set_int_ctrl KEYWORD2 13 | kx13x_set_int_route KEYWORD2 14 | kx13x_get_adp_data KEYWORD2 15 | kx13x_get_adp_data_raw KEYWORD2 16 | kx13x_set_adp_cfg KEYWORD2 17 | kx13x_set_wu_bts_cfg KEYWORD2 18 | kx13x_get_accel_data KEYWORD2 19 | kx13x_get_accel_data_raw KEYWORD2 20 | kx13x_set_accel_cfg KEYWORD2 21 | kx13x_set_avg_filter_ctrl KEYWORD2 22 | kx13x_set_low_pass_filter KEYWORD2 23 | kx13x_set_drdy_enabled KEYWORD2 24 | kx13x_set_odr KEYWORD2 25 | kx13x_set_grange KEYWORD2 26 | kx13x_set_perf_mode KEYWORD2 27 | kx13x_get_oper_mode KEYWORD2 28 | kx13x_set_oper_mode KEYWORD2 29 | kx13x_example_handle_interrupt KEYWORD2 30 | kx13x_example_poll_interrupt KEYWORD2 31 | 32 | -------------------------------------------------------------------------------- /kx13x/kx13x.c: -------------------------------------------------------------------------------- 1 | /* 2 | The MIT License (MIT) 3 | Copyright (c) 2020 ROHM Co.,Ltd. 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a 6 | copy of this software and associated documentation files (the 7 | "Software"), to deal in the Software without restriction, including 8 | without limitation the rights to use, copy, modify, merge, publish, 9 | distribute, sublicense, and/or sell copies of the Software, and to 10 | permit persons to whom the Software is furnished to do so, subject to 11 | the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included 14 | in all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 17 | OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 18 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 19 | IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY 20 | CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 21 | TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 22 | SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 23 | */ 24 | 25 | #include 26 | #include 27 | #include 28 | 29 | #include "platform.h" 30 | #include "kx13x.h" 31 | #include "kx132_1211_registers.h" 32 | #include "kx134_1211_registers.h" 33 | 34 | #define UNUSED_VAR(a) (void)a 35 | 36 | /* Macro to enable debug prints */ 37 | #define KX13X_DEBUG 38 | 39 | #ifdef KX13X_DEBUG 40 | #define KX13X_TRACE_STR(dev,str) kx13x_debug_print_str(dev,str) 41 | #define KX13X_TRACE_STR_1(dev,str,aa) kx13x_debug_print_str_1(dev,str,aa) 42 | #define KX13X_TRACE_STR_2(dev,str,aa,bb) kx13x_debug_print_str_2(dev,str,aa,bb) 43 | #else 44 | #define KX13X_TRACE_STR(dev,str) 45 | #define KX13X_TRACE_STR_1(dev,str,aa) 46 | #define KX13X_TRACE_STR_2(dev,str,aa,bb) 47 | #endif 48 | 49 | #define ARRAY_SIZE(a) (sizeof(a)/sizeof(a[0])) 50 | 51 | /* Supported sensors info */ 52 | struct kx13x_sensor_info 53 | { 54 | uint8_t type; 55 | char name[11]; 56 | uint8_t wai_id; 57 | uint16_t granges; 58 | }; 59 | 60 | static struct kx13x_sensor_info kx13x_supported_sensors[] = 61 | { 62 | { 63 | .type = KX13X_TYPE_KX132_1211, 64 | .name = "KX132-1211", 65 | .wai_id = KX132_1211_WHO_AM_I_WAI_ID, 66 | .granges = (KX13X_GRANGE_2G|KX13X_GRANGE_4G|KX13X_GRANGE_8G|KX13X_GRANGE_16G) 67 | }, 68 | { 69 | .type = KX13X_TYPE_KX134_1211, 70 | .name = "KX134-1211", 71 | .wai_id = KX134_1211_WHO_AM_I_WAI_ID, 72 | .granges = (KX13X_GRANGE_8G|KX13X_GRANGE_16G|KX13X_GRANGE_32G|KX13X_GRANGE_64G) 73 | }, 74 | }; 75 | 76 | static struct kx13x_sensor_info* kx13x_sensors_info_is_supported(uint8_t wai_id) 77 | { 78 | struct kx13x_sensor_info *sensor = NULL; 79 | uint16_t i; 80 | 81 | for (i = 0; i < ARRAY_SIZE(kx13x_supported_sensors); i++) { 82 | if (kx13x_supported_sensors[i].wai_id == wai_id) { 83 | sensor = (struct kx13x_sensor_info *)&kx13x_supported_sensors[i]; 84 | break; 85 | } 86 | } 87 | 88 | return sensor; 89 | } 90 | 91 | /* Platform debug print */ 92 | int kx13x_platform_debug_print(struct platform *plat, char *str) 93 | { 94 | if (plat->debug_print) 95 | plat->debug_print(plat, str); 96 | 97 | return KX13X_RC_OK; 98 | } 99 | 100 | /* Platform delay function */ 101 | int kx13x_platform_delay_ms(struct platform *plat, uint16_t ms) 102 | { 103 | return plat->delay_ms(plat, ms); 104 | } 105 | 106 | /* Platform sensor bus register read/write */ 107 | int kx13x_platform_read(struct platform *plat, uint8_t reg, uint8_t *data, uint8_t size) 108 | { 109 | return plat->read(plat, reg, data, size); 110 | } 111 | 112 | int kx13x_platform_write(struct platform *plat, uint8_t reg, uint8_t *data, uint8_t size) 113 | { 114 | return plat->write(plat, reg, data, size); 115 | } 116 | 117 | /* Sensor driver register read/write */ 118 | int kx13x_read_reg(struct kx13x *dev, uint8_t reg, uint8_t *data, uint8_t size) 119 | { 120 | return kx13x_platform_read(dev->plat, reg, data, size); 121 | } 122 | 123 | int kx13x_write_reg(struct kx13x *dev, uint8_t reg, uint8_t *data, uint8_t size) 124 | { 125 | return kx13x_platform_write(dev->plat, reg, data, size); 126 | } 127 | 128 | int kx13x_read_reg_byte(struct kx13x *dev, uint8_t reg, uint8_t *data) 129 | { 130 | return kx13x_read_reg(dev, reg, data, 1); 131 | } 132 | 133 | int kx13x_write_reg_byte(struct kx13x *dev, uint8_t reg, uint8_t data) 134 | { 135 | return kx13x_write_reg(dev, reg, &data, 1); 136 | } 137 | 138 | int kx13x_set_reg_bit_pattern(struct kx13x *dev, uint8_t reg, uint8_t bit_pattern, uint8_t mask) 139 | { 140 | int rc; 141 | uint8_t reg_val; 142 | 143 | rc = kx13x_read_reg_byte(dev, reg, ®_val); 144 | if (rc != KX13X_RC_OK) { 145 | return rc; 146 | } 147 | 148 | reg_val &= ~mask; 149 | reg_val |= (bit_pattern & mask); 150 | 151 | rc = kx13x_write_reg_byte(dev, reg, reg_val); 152 | if (rc != KX13X_RC_OK) { 153 | return rc; 154 | } 155 | 156 | return KX13X_RC_OK; 157 | } 158 | 159 | int kx13x_set_reg_bit(struct kx13x *dev, uint8_t reg, uint8_t bits) 160 | { 161 | int rc; 162 | uint8_t reg_val; 163 | 164 | rc = kx13x_read_reg_byte(dev, reg, ®_val); 165 | if (rc != KX13X_RC_OK) { 166 | return rc; 167 | } 168 | 169 | reg_val |= bits; 170 | 171 | return kx13x_write_reg_byte(dev, reg, reg_val); 172 | } 173 | 174 | int kx13x_reset_reg_bit(struct kx13x *dev, uint8_t reg, uint8_t bits) 175 | { 176 | int rc; 177 | uint8_t reg_val; 178 | 179 | rc = kx13x_read_reg_byte(dev, reg, ®_val); 180 | if (rc != KX13X_RC_OK) { 181 | return rc; 182 | } 183 | 184 | reg_val &= ~bits; 185 | 186 | return kx13x_write_reg_byte(dev, reg, reg_val); 187 | } 188 | 189 | /* kx13x.h define to reg mapping and get/set functions*/ 190 | struct kx13x_define_reg_bits { 191 | uint8_t _define; 192 | uint8_t _reg_bits; 193 | }; 194 | 195 | struct kx13x_define_reg_map { 196 | uint8_t reg; 197 | uint8_t mask; 198 | uint8_t amount; 199 | struct kx13x_define_reg_bits values[]; 200 | }; 201 | 202 | int kx13x_map_to_reg_bits(struct kx13x_define_reg_map *map, uint8_t _define, uint8_t *_reg_bits) 203 | { 204 | int rc = KX13X_RC_INVALID_PARAM; 205 | uint16_t i; 206 | 207 | for (i = 0; i < map->amount; i++) { 208 | if (map->values[i]._define == _define) { 209 | *_reg_bits = map->values[i]._reg_bits; 210 | rc = KX13X_RC_OK; 211 | break; 212 | } 213 | } 214 | 215 | return rc; 216 | } 217 | 218 | int kx13x_map_to_define_val(struct kx13x_define_reg_map *map, uint8_t _reg_bits, uint8_t *_define) 219 | { 220 | int rc = KX13X_RC_INVALID_PARAM; 221 | uint16_t i; 222 | 223 | uint8_t reg_bits = map->mask & _reg_bits; 224 | 225 | for (i = 0; i < map->amount; i++) { 226 | if (map->values[i]._reg_bits == reg_bits) { 227 | *_define = map->values[i]._define; 228 | rc = KX13X_RC_OK; 229 | break; 230 | } 231 | } 232 | 233 | return rc; 234 | } 235 | 236 | int kx13x_set_map_reg_bits(struct kx13x *dev, struct kx13x_define_reg_map *map, uint8_t _define) 237 | { 238 | int rc; 239 | uint8_t reg_val; 240 | 241 | rc = kx13x_map_to_reg_bits(map, _define, ®_val); 242 | if (rc != KX13X_RC_OK) { 243 | return rc; 244 | } 245 | 246 | rc = kx13x_set_reg_bit_pattern(dev, map->reg, reg_val, map->mask); 247 | if (rc != KX13X_RC_OK) { 248 | return rc; 249 | } 250 | 251 | return KX13X_RC_OK; 252 | } 253 | 254 | /* Debug */ 255 | #ifdef KX13X_DEBUG 256 | static void kx13x_debug_print_str(struct kx13x *dev, char *str) 257 | { 258 | kx13x_platform_debug_print(dev->plat, str); 259 | } 260 | 261 | static void kx13x_debug_print_str_1(struct kx13x *dev, char *str, int val1) 262 | { 263 | char buffer[100]; 264 | (void)sprintf(buffer, str, val1); 265 | kx13x_platform_debug_print(dev->plat, buffer); 266 | } 267 | 268 | static void kx13x_debug_print_str_2(struct kx13x *dev, char *str, int val1, int val2) 269 | { 270 | char buffer[100]; 271 | (void)sprintf(buffer, str, val1, val2); 272 | kx13x_platform_debug_print(dev->plat, buffer); 273 | } 274 | #endif 275 | 276 | int kx13x_debug_dump_regs(struct kx13x *dev) 277 | { 278 | #ifdef KX13X_DEBUG 279 | int rc; 280 | uint8_t dump_regs[] = { 281 | KX132_1211_STATUS_REG, 282 | KX132_1211_CNTL1, 283 | KX132_1211_CNTL2, 284 | KX132_1211_CNTL3, 285 | KX132_1211_CNTL4, 286 | KX132_1211_CNTL5, 287 | KX132_1211_ODCNTL, 288 | KX132_1211_INC1, 289 | KX132_1211_INC2, 290 | KX132_1211_INC3, 291 | KX132_1211_INC4, 292 | KX132_1211_INC5, 293 | KX132_1211_INC6, 294 | KX132_1211_LP_CNTL1 295 | }; 296 | uint8_t reg_val; 297 | uint8_t i; 298 | 299 | KX13X_TRACE_STR(dev, "kx13x_debug_dump_regs:\n"); 300 | 301 | for (i=0; i < ARRAY_SIZE(dump_regs); i++) { 302 | rc = kx13x_read_reg_byte(dev, dump_regs[i], ®_val); 303 | if (rc != KX13X_RC_OK) { 304 | return rc; 305 | } 306 | 307 | KX13X_TRACE_STR_2(dev, "reg 0x%x val 0x%x\n",dump_regs[i],reg_val); 308 | } 309 | #else 310 | UNUSED_VAR(dev); 311 | #endif 312 | return KX13X_RC_OK; 313 | } 314 | 315 | /* Operation mode */ 316 | int kx13x_set_oper_mode(struct kx13x *dev, uint8_t oper) 317 | { 318 | int rc; 319 | 320 | switch(oper) { 321 | case KX13X_OPER_MODE_OPERATING: 322 | rc = kx13x_set_reg_bit(dev, KX132_1211_CNTL1, KX132_1211_CNTL1_PC1); 323 | break; 324 | case KX13X_OPER_MODE_STANDBY: 325 | rc = kx13x_reset_reg_bit(dev, KX132_1211_CNTL1, KX132_1211_CNTL1_PC1); 326 | break; 327 | default: 328 | rc = KX13X_RC_INVALID_PARAM; 329 | break; 330 | } 331 | 332 | return rc; 333 | } 334 | 335 | int kx13x_get_oper_mode(struct kx13x *dev, uint8_t *oper) 336 | { 337 | int rc; 338 | uint8_t reg_val; 339 | 340 | rc = kx13x_read_reg_byte(dev, KX132_1211_CNTL1, ®_val); 341 | if (rc != KX13X_RC_OK) { 342 | return rc; 343 | } 344 | 345 | if (reg_val & KX132_1211_CNTL1_PC1) { 346 | *oper = KX13X_OPER_MODE_OPERATING; 347 | } else { 348 | *oper = KX13X_OPER_MODE_STANDBY; 349 | } 350 | 351 | return KX13X_RC_OK; 352 | } 353 | 354 | /* Perf mode */ 355 | int kx13x_set_perf_mode(struct kx13x *dev, uint8_t perf) 356 | { 357 | int rc; 358 | 359 | switch(perf) { 360 | case KX13X_PERF_MODE_LOW_POWER: 361 | rc = kx13x_reset_reg_bit(dev, KX132_1211_CNTL1, KX132_1211_CNTL1_RES); 362 | break; 363 | case KX13X_PERF_MODE_HIGH_RES: 364 | rc = kx13x_set_reg_bit(dev, KX132_1211_CNTL1, KX132_1211_CNTL1_RES); 365 | break; 366 | default: 367 | rc = KX13X_RC_INVALID_PARAM; 368 | break; 369 | } 370 | 371 | return rc; 372 | } 373 | 374 | /* grange */ 375 | static struct kx13x_define_reg_map grange16_map = 376 | { 377 | .reg = KX132_1211_CNTL1, 378 | .mask = KX132_1211_CNTL1_GSEL_MASK, 379 | .amount = 4, 380 | .values = { 381 | { 382 | ._define = KX13X_GRANGE_2G, 383 | ._reg_bits = KX132_1211_CNTL1_GSEL_2G, 384 | }, 385 | { 386 | ._define = KX13X_GRANGE_4G, 387 | ._reg_bits = KX132_1211_CNTL1_GSEL_4G, 388 | }, 389 | { 390 | ._define = KX13X_GRANGE_8G, 391 | ._reg_bits = KX132_1211_CNTL1_GSEL_8G, 392 | }, 393 | { 394 | ._define = KX13X_GRANGE_16G, 395 | ._reg_bits = KX132_1211_CNTL1_GSEL_16G, 396 | }, 397 | } 398 | }; 399 | 400 | static struct kx13x_define_reg_map grange64_map = 401 | { 402 | .reg = KX134_1211_CNTL1, 403 | .mask = KX134_1211_CNTL1_GSEL_MASK, 404 | .amount = 4, 405 | .values = { 406 | { 407 | ._define = KX13X_GRANGE_8G, 408 | ._reg_bits = KX134_1211_CNTL1_GSEL_8G, 409 | }, 410 | { 411 | ._define = KX13X_GRANGE_16G, 412 | ._reg_bits = KX134_1211_CNTL1_GSEL_16G, 413 | }, 414 | { 415 | ._define = KX13X_GRANGE_32G, 416 | ._reg_bits = KX134_1211_CNTL1_GSEL_32G, 417 | }, 418 | { 419 | ._define = KX13X_GRANGE_64G, 420 | ._reg_bits = KX134_1211_CNTL1_GSEL_64G, 421 | }, 422 | } 423 | }; 424 | 425 | /* calculate 1g LSB counts, 16bit counts div by selected -/+ range */ 426 | #define KX13X_GRANGE_TO_GSENS(enum_g) (0x10000 / (enum_g*2)) 427 | 428 | int kx13x_set_grange(struct kx13x *dev, uint8_t grange) 429 | { 430 | int rc; 431 | struct kx13x_define_reg_map *map; 432 | 433 | if (!(dev->granges & grange)) { 434 | return KX13X_RC_NOT_SUPPORTED; 435 | } 436 | 437 | if (dev->granges & KX13X_GRANGE_64G) { 438 | /* Note, check 64G first */ 439 | map = &grange64_map; 440 | } else { 441 | map = &grange16_map; 442 | } 443 | 444 | rc = kx13x_set_map_reg_bits(dev, map, grange); 445 | if (rc != KX13X_RC_OK) { 446 | return rc; 447 | } 448 | 449 | dev->gsens = KX13X_GRANGE_TO_GSENS(grange); 450 | 451 | return KX13X_RC_OK; 452 | } 453 | 454 | int kx13x_set_odr(struct kx13x *dev, uint8_t odr) 455 | { 456 | int rc; 457 | rc = kx13x_set_reg_bit_pattern(dev, KX132_1211_ODCNTL, odr, KX132_1211_ODCNTL_OSA_MASK); 458 | return rc; 459 | } 460 | 461 | /* Enable DRDY */ 462 | int kx13x_set_drdy_enabled(struct kx13x *dev, uint8_t enable) 463 | { 464 | int rc; 465 | 466 | switch(enable) { 467 | case KX13X_ENABLED: 468 | rc = kx13x_set_reg_bit(dev, KX132_1211_CNTL1, KX132_1211_CNTL1_DRDYE); 469 | break; 470 | case KX13X_DISABLED: 471 | rc = kx13x_reset_reg_bit(dev, KX132_1211_CNTL1, KX132_1211_CNTL1_DRDYE); 472 | break; 473 | default: 474 | rc = KX13X_RC_INVALID_PARAM; 475 | break; 476 | } 477 | 478 | return rc; 479 | } 480 | 481 | /* Lowpass / bybass */ 482 | static struct kx13x_define_reg_map bypass_map = 483 | { 484 | .reg = KX132_1211_ODCNTL, 485 | .mask = (KX132_1211_ODCNTL_LPRO_MASK), 486 | .amount = KX13X_BYPASS_AMOUNT, 487 | .values = { 488 | { 489 | ._define = KX13X_BYPASS_ODR_2, 490 | ._reg_bits = KX132_1211_ODCNTL_LPRO_ODR_2, 491 | }, 492 | { 493 | ._define = KX13X_BYPASS_ODR_9, 494 | ._reg_bits = KX132_1211_ODCNTL_LPRO_ODR_9, 495 | }, 496 | } 497 | }; 498 | 499 | int kx13x_set_low_pass_filter(struct kx13x *dev, uint8_t filter) 500 | { 501 | int rc; 502 | uint8_t reg_val; 503 | 504 | rc = kx13x_map_to_reg_bits(&bypass_map, filter, ®_val); 505 | if (rc != KX13X_RC_OK) { 506 | return rc; 507 | } 508 | 509 | rc = kx13x_set_reg_bit_pattern(dev, bypass_map.reg, reg_val, bypass_map.mask); 510 | if (rc != KX13X_RC_OK) { 511 | return rc; 512 | } 513 | 514 | return KX13X_RC_OK; 515 | } 516 | 517 | /* Average filter */ 518 | static struct kx13x_define_reg_map avg_map = 519 | { 520 | .reg = KX132_1211_LP_CNTL1, 521 | .mask = KX132_1211_LP_CNTL1_AVC_MASK, 522 | .amount = KX13X_AVG_AMOUNT, 523 | .values = { 524 | { 525 | ._define = KX13X_AVG_NO_AVG, 526 | ._reg_bits = KX132_1211_LP_CNTL1_AVC_NO_AVG, 527 | }, 528 | { 529 | ._define = KX13X_AVG_2_SAMPLE, 530 | ._reg_bits = KX132_1211_LP_CNTL1_AVC_2_SAMPLE_AVG, 531 | }, 532 | { 533 | ._define = KX13X_AVG_4_SAMPLE, 534 | ._reg_bits = KX132_1211_LP_CNTL1_AVC_4_SAMPLE_AVG, 535 | }, 536 | { 537 | ._define = KX13X_AVG_8_SAMPLE, 538 | ._reg_bits = KX132_1211_LP_CNTL1_AVC_8_SAMPLE_AVG, 539 | }, 540 | { 541 | ._define = KX13X_AVG_32_SAMPLE, 542 | ._reg_bits = KX132_1211_LP_CNTL1_AVC_32_SAMPLE_AVG, 543 | }, 544 | { 545 | ._define = KX13X_AVG_16_SAMPLE, 546 | ._reg_bits = KX132_1211_LP_CNTL1_AVC_16_SAMPLE_AVG, 547 | }, 548 | { 549 | ._define = KX13X_AVG_64_SAMPLE, 550 | ._reg_bits = KX132_1211_LP_CNTL1_AVC_64_SAMPLE_AVG, 551 | }, 552 | 553 | } 554 | }; 555 | 556 | int kx13x_set_avg_filter_ctrl(struct kx13x *dev, uint8_t avc) 557 | { 558 | int rc; 559 | uint8_t reg_val; 560 | 561 | rc = kx13x_map_to_reg_bits(&avg_map, avc, ®_val); 562 | if (rc != KX13X_RC_OK) { 563 | return rc; 564 | } 565 | 566 | rc = kx13x_set_reg_bit_pattern(dev, avg_map.reg, reg_val, avg_map.mask); 567 | if (rc != KX13X_RC_OK) { 568 | return rc; 569 | } 570 | 571 | return KX13X_RC_OK; 572 | } 573 | 574 | /* Get accel data */ 575 | int kx13x_get_accel_data_raw(struct kx13x *dev, int16_t *xyz_raw) 576 | { 577 | int rc; 578 | uint8_t xyz[6]; 579 | 580 | rc = kx13x_read_reg(dev, KX132_1211_XOUT_L, (uint8_t*)xyz, 6); 581 | if (rc != KX13X_RC_OK) 582 | { 583 | return rc; 584 | } 585 | 586 | xyz_raw[0] = ((int16_t)xyz[0]) | (((int16_t)xyz[1]) << 8); 587 | xyz_raw[1] = ((int16_t)xyz[2]) | (((int16_t)xyz[3]) << 8); 588 | xyz_raw[2] = ((int16_t)xyz[4]) | (((int16_t)xyz[5]) << 8); 589 | 590 | return KX13X_RC_OK; 591 | } 592 | 593 | int kx13x_get_accel_data(struct kx13x *dev, float *xyz) 594 | { 595 | int16_t raw_xyz[3]; 596 | int rc; 597 | 598 | rc = kx13x_get_accel_data_raw(dev, &raw_xyz[0]); 599 | if (rc != KX13X_RC_OK) 600 | { 601 | return rc; 602 | } 603 | 604 | xyz[0] = (float)raw_xyz[0] / dev->gsens; 605 | xyz[1] = (float)raw_xyz[1] / dev->gsens; 606 | xyz[2] = (float)raw_xyz[2] / dev->gsens; 607 | 608 | return KX13X_RC_OK; 609 | } 610 | 611 | int kx13x_set_accel_cfg(struct kx13x *dev, struct kx13x_accel_cfg *cfg) 612 | { 613 | int rc; 614 | 615 | rc = kx13x_set_perf_mode(dev, cfg->perf_mode); 616 | if (rc != KX13X_RC_OK) { 617 | return rc; 618 | } 619 | 620 | rc = kx13x_set_grange(dev, cfg->grange); 621 | if (rc != KX13X_RC_OK) { 622 | return rc; 623 | } 624 | 625 | rc = kx13x_set_odr(dev, cfg->odr); 626 | if (rc != KX13X_RC_OK) { 627 | return rc; 628 | } 629 | 630 | rc = kx13x_set_drdy_enabled(dev, cfg->drdy_enable); 631 | if (rc != KX13X_RC_OK) { 632 | return rc; 633 | } 634 | 635 | rc = kx13x_set_low_pass_filter(dev, cfg->filter); 636 | if (rc != KX13X_RC_OK) { 637 | return rc; 638 | } 639 | 640 | rc = kx13x_set_avg_filter_ctrl(dev, cfg->avc); 641 | if (rc != KX13X_RC_OK) { 642 | return rc; 643 | } 644 | 645 | return KX13X_RC_OK; 646 | } 647 | 648 | /* Wake-up/back to sleep */ 649 | int kx13x_set_wu_bts_cfg(struct kx13x *dev, struct kx13x_wu_bts_cfg *cfg) 650 | { 651 | int rc; 652 | uint8_t cntl4 = 0; 653 | uint8_t bts_wuf_th_hibits = 0; 654 | uint8_t reg_val; 655 | 656 | /* Wake-up settings */ 657 | if (cfg->wu) { 658 | 659 | if (cfg->wu->enable) { 660 | cntl4 |= KX132_1211_CNTL4_WUFE_ENABLED; 661 | } 662 | 663 | /* wu threshold lo-8bits */ 664 | reg_val = cfg->wu->threshold & 0xff; 665 | rc = kx13x_write_reg_byte(dev, KX132_1211_WUFTH, reg_val); 666 | if (rc != KX13X_RC_OK) { 667 | return rc; 668 | } 669 | 670 | /* wu threshold hi-3bits to BTSWUFTH lo-nibble */ 671 | bts_wuf_th_hibits = ((cfg->wu->threshold >> 8) & 0x07); 672 | 673 | /* wu counter */ 674 | rc = kx13x_write_reg_byte(dev, KX132_1211_WUFC, cfg->wu->counter); 675 | if (rc != KX13X_RC_OK) { 676 | return rc; 677 | } 678 | 679 | /* wu odr */ 680 | rc = kx13x_set_reg_bit_pattern(dev, KX132_1211_CNTL3, cfg->wu->odr, KX132_1211_CNTL3_OWUF_MASK); 681 | if (rc != KX13X_RC_OK) { 682 | return rc; 683 | } 684 | } 685 | 686 | /* Back to sleep settings */ 687 | if (cfg->bts) { 688 | 689 | if (cfg->bts->enable) { 690 | cntl4 |= KX132_1211_CNTL4_BTSE_ENABLED; 691 | } 692 | 693 | /* bts threshold lo-8bits */ 694 | reg_val = cfg->bts->threshold & 0xff; 695 | rc = kx13x_write_reg_byte(dev, KX132_1211_BTSTH, reg_val); 696 | if (rc != KX13X_RC_OK) { 697 | return rc; 698 | } 699 | /* bts threshold hi-3bits to BTSWUFTH hi-nibble */ 700 | bts_wuf_th_hibits |= ((cfg->bts->threshold >> 8) & 0x07) << 4; 701 | 702 | /* bts counter */ 703 | rc = kx13x_write_reg_byte(dev, KX132_1211_BTSC, cfg->bts->counter); 704 | if (rc != KX13X_RC_OK) { 705 | return rc; 706 | } 707 | 708 | /* bts odr */ 709 | cntl4 |= cfg->bts->odr; 710 | } 711 | 712 | /* set bts_wuf_th_hibits */ 713 | rc = kx13x_write_reg_byte(dev, KX132_1211_BTSWUFTH, bts_wuf_th_hibits); 714 | if (rc != KX13X_RC_OK) { 715 | return rc; 716 | } 717 | 718 | /* direction mask and occurrence */ 719 | rc = kx13x_write_reg_byte(dev, KX132_1211_INC2, cfg->axes_bits); 720 | if (rc != KX13X_RC_OK) { 721 | return rc; 722 | } 723 | 724 | /* set wu/bts mode bits and write CNTL4 */ 725 | cntl4 |= cfg->mode_bits; 726 | 727 | rc = kx13x_write_reg_byte(dev, KX132_1211_CNTL4, cntl4); 728 | if (rc != KX13X_RC_OK) { 729 | return rc; 730 | } 731 | 732 | /* manual force */ 733 | rc = kx13x_set_reg_bit(dev, KX132_1211_CNTL5, KX132_1211_CNTL5_MAN_WAKE); 734 | if (rc != KX13X_RC_OK) { 735 | return rc; 736 | } 737 | 738 | return KX13X_RC_OK; 739 | } 740 | /* Advanced data path (ADP) */ 741 | struct f1_filter { 742 | uint8_t f1_1a; /* <6:0> */ 743 | uint32_t f1_ba; /* <22:0> */ 744 | uint32_t f1_ca; /* <22:0> */ 745 | uint8_t f1_ish; /* <4:0> */ 746 | uint8_t f1_osh; /* <0> bit */ 747 | }; 748 | 749 | struct f1_filter pre_def_f1_filters[] = 750 | { 751 | {22, 0, 1439258, 1, 1}, 752 | {72, 3954428, 2796203, 2, 0}, 753 | {117, 6099540, 4815580, 4, 0}, 754 | {10, 7230041, 6354764, 5, 0}, 755 | {20, 7807115, 7301172, 7, 0}, 756 | {25, 8097550, 7826024, 9, 0}, 757 | {27, 8243038, 8102435, 11, 0}, 758 | {29, 8315818, 8244280, 13, 0}, 759 | {29, 8352212, 8316131, 15, 0}, 760 | {30, 8370410, 8352291, 17, 0}, 761 | {15,2934914,2176803,1,0}, 762 | {52, 4213708, 2986360, 2, 0}, 763 | {18, 4674381, 3358701, 2, 0}, 764 | }; 765 | 766 | int kx13x_set_adp_filter1(struct kx13x *dev, uint8_t filter1) 767 | { 768 | int rc; 769 | struct f1_filter *f1; 770 | 771 | if (filter1 == KX13X_ADP_FILTER1_NONE) { 772 | /* disable filter1 */ 773 | rc = kx13x_set_reg_bit(dev, KX132_1211_ADP_CNTL2, KX132_1211_ADP_CNTL2_ADP_FLT1_BYP); 774 | return rc; 775 | } 776 | 777 | /* enable filter1 */ 778 | rc = kx13x_reset_reg_bit(dev, KX132_1211_ADP_CNTL2, KX132_1211_ADP_CNTL2_ADP_FLT1_BYP); 779 | if (rc != KX13X_RC_OK) { 780 | return rc; 781 | } 782 | 783 | /* get filter parameters */ 784 | f1 = &pre_def_f1_filters[filter1]; 785 | 786 | /* set filter1 parameters */ 787 | rc = kx13x_write_reg_byte(dev, KX134_1211_ADP_CNTL3, f1->f1_1a); 788 | if (rc != KX13X_RC_OK) { 789 | return rc; 790 | } 791 | rc = kx13x_write_reg_byte(dev, KX134_1211_ADP_CNTL4, f1->f1_ba & 0xff); 792 | if (rc != KX13X_RC_OK) { 793 | return rc; 794 | } 795 | rc = kx13x_write_reg_byte(dev, KX134_1211_ADP_CNTL5, (f1->f1_ba >> 8) & 0xff); 796 | if (rc != KX13X_RC_OK) { 797 | return rc; 798 | } 799 | rc = kx13x_write_reg_byte(dev, KX134_1211_ADP_CNTL6, (f1->f1_ba >> 16) & 0x7f); 800 | if (rc != KX13X_RC_OK) { 801 | return rc; 802 | } 803 | rc = kx13x_write_reg_byte(dev, KX134_1211_ADP_CNTL7, f1->f1_ca & 0xff); 804 | if (rc != KX13X_RC_OK) { 805 | return rc; 806 | } 807 | rc = kx13x_write_reg_byte(dev, KX134_1211_ADP_CNTL8, (f1->f1_ca >> 8) & 0xff); 808 | if (rc != KX13X_RC_OK) { 809 | return rc; 810 | } 811 | rc = kx13x_write_reg_byte(dev, KX134_1211_ADP_CNTL9, (f1->f1_ca >> 16) & 0x7f); 812 | if (rc != KX13X_RC_OK) { 813 | return rc; 814 | } 815 | rc = kx13x_write_reg_byte(dev, KX134_1211_ADP_CNTL10, f1->f1_ish); 816 | if (rc != KX13X_RC_OK) { 817 | return rc; 818 | } 819 | rc = kx13x_set_reg_bit_pattern(dev, KX134_1211_ADP_CNTL11, f1->f1_osh << 7, KX134_1211_ADP_CNTL11_ADP_F1_OSH); 820 | 821 | return rc; 822 | } 823 | 824 | struct f2_filter { 825 | uint8_t f2_1a; /* <6:0> */ 826 | uint16_t f2_ba; /* <14:0> */ 827 | uint8_t f2_ish; /* <4:0> */ 828 | uint8_t f2_osh; /* <4:0> */ 829 | }; 830 | 831 | struct f2_filter pre_def_f2_filters[] = 832 | { 833 | {0, 0, 1, 1}, 834 | {22, 13573, 1, 0}, 835 | {42, 21895, 2, 0}, 836 | {56, 26892, 3, 0}, 837 | {64, 29699, 4, 0}, 838 | {68, 31198, 5, 0}, 839 | {71, 31973, 6, 0}, 840 | {72, 32368, 7, 0}, 841 | {72, 32568, 8, 0}, 842 | {73, 32668, 9, 0}, 843 | {33, 22481, 2, 0}, 844 | {0, 0, 1, 1}, 845 | {53, 13573, 2, 2}, 846 | {86, 21895, 3, 3}, 847 | {105, 26892, 4, 4}, 848 | {109, 27987, 4, 4}, 849 | {116, 29699, 5, 5}, 850 | {122, 31198, 6, 6}, 851 | {125, 31973, 7, 7}, 852 | {126, 32368, 8, 8}, 853 | {127, 32448, 8, 8}, 854 | {127, 32568, 9, 9}, 855 | {0, 32668, 9, 10}, 856 | {77, 19640, 3, 3}, 857 | {59, 15006, 2, 2}, 858 | {57, 14523, 2, 2}, 859 | {30, 7779, 2, 2}, 860 | {52, 13336, 2, 2} 861 | }; 862 | 863 | int kx13x_set_adp_filter2(struct kx13x *dev, uint8_t filter2) 864 | { 865 | int rc; 866 | struct f2_filter *f2; 867 | 868 | if (filter2 == KX13X_ADP_FILTER2_NONE) { 869 | /* disable filter2 */ 870 | rc = kx13x_set_reg_bit(dev, KX132_1211_ADP_CNTL2, KX134_1211_ADP_CNTL2_ADP_FLT2_BYP); 871 | return rc; 872 | } 873 | 874 | /* enable filter2 */ 875 | rc = kx13x_reset_reg_bit(dev, KX132_1211_ADP_CNTL2, KX134_1211_ADP_CNTL2_ADP_FLT2_BYP); 876 | if (rc != KX13X_RC_OK) { 877 | return rc; 878 | } 879 | 880 | /* set filter2 to LP/HP */ 881 | if (filter2 < KX13X_ADP_FILTER2_HP_FILTERS) { 882 | rc = kx13x_reset_reg_bit(dev, KX134_1211_ADP_CNTL2, KX134_1211_ADP_CNTL2_ADP_F2_HP); 883 | } else { 884 | rc = kx13x_set_reg_bit(dev, KX134_1211_ADP_CNTL2, KX134_1211_ADP_CNTL2_ADP_F2_HP); 885 | } 886 | if (rc != KX13X_RC_OK) { 887 | return rc; 888 | } 889 | 890 | /* get filter2 parameters */ 891 | f2 = &pre_def_f2_filters[filter2]; 892 | 893 | /* set filter2 parameters */ 894 | rc = kx13x_write_reg_byte(dev, KX134_1211_ADP_CNTL12, f2->f2_ba & 255); 895 | if (rc != KX13X_RC_OK) { 896 | return rc; 897 | } 898 | rc = kx13x_write_reg_byte(dev, KX134_1211_ADP_CNTL13, (f2->f2_ba >> 8) & 255); 899 | if (rc != KX13X_RC_OK) { 900 | return rc; 901 | } 902 | rc = kx13x_write_reg_byte(dev, KX134_1211_ADP_CNTL18, f2->f2_ish); 903 | if (rc != KX13X_RC_OK) { 904 | return rc; 905 | } 906 | rc = kx13x_write_reg_byte(dev, KX134_1211_ADP_CNTL19, f2->f2_osh); 907 | if (rc != KX13X_RC_OK) { 908 | return rc; 909 | } 910 | 911 | rc = kx13x_set_reg_bit_pattern(dev, KX134_1211_ADP_CNTL11, f2->f2_1a, KX134_1211_ADP_CNTL11_ADP_F2_1A_MASK); 912 | 913 | return rc; 914 | } 915 | 916 | int kx13x_set_adp_odr(struct kx13x *dev, uint8_t adp_odr) 917 | { 918 | int rc; 919 | rc = kx13x_set_reg_bit_pattern(dev, KX132_1211_ADP_CNTL1, adp_odr, KX132_1211_ADP_CNTL1_OADP_MASK); 920 | return rc; 921 | } 922 | 923 | int kx13x_set_adp_rms_avg(struct kx13x *dev, uint8_t rms_avg) 924 | { 925 | int rc; 926 | 927 | if (rms_avg == KX13X_ADP_RMS_AVC_NONE) { 928 | /* Route ADP data before RMS block to XADP, YADP, ZADP */ 929 | rc = kx13x_reset_reg_bit(dev, KX134_1211_ADP_CNTL2, KX134_1211_ADP_CNTL2_ADP_RMS_OSEL); 930 | } else { 931 | /* Route ADP data after RMS block to XADP, YADP, ZADP */ 932 | rc = kx13x_set_reg_bit(dev, KX134_1211_ADP_CNTL2, KX134_1211_ADP_CNTL2_ADP_RMS_OSEL); 933 | if (rc != KX13X_RC_OK) { 934 | return rc; 935 | } 936 | 937 | rc = kx13x_set_reg_bit_pattern(dev, KX134_1211_ADP_CNTL1, rms_avg, 938 | KX134_1211_ADP_CNTL1_RMS_AVC_MASK); 939 | } 940 | 941 | return rc; 942 | } 943 | 944 | int kx13x_set_adp_enabled(struct kx13x *dev, uint8_t enable) 945 | { 946 | int rc; 947 | 948 | if (enable == KX13X_ENABLED) { 949 | rc = kx13x_set_reg_bit(dev, KX134_1211_CNTL5, KX132_1211_CNTL5_ADPE_ENABLED); 950 | } else { 951 | rc = kx13x_reset_reg_bit(dev, KX134_1211_CNTL5, KX132_1211_CNTL5_ADPE_ENABLED); 952 | } 953 | 954 | return rc; 955 | } 956 | 957 | int kx13x_set_adp_cfg(struct kx13x *dev, struct kx13x_adp_cfg *cfg) 958 | { 959 | int rc; 960 | 961 | rc = kx13x_set_adp_filter1(dev, cfg->filter1); 962 | if (rc != KX13X_RC_OK) { 963 | return rc; 964 | } 965 | 966 | rc = kx13x_set_adp_filter2(dev, cfg->filter2); 967 | if (rc != KX13X_RC_OK) { 968 | return rc; 969 | } 970 | 971 | rc = kx13x_set_adp_odr(dev, cfg->adp_odr); 972 | if (rc != KX13X_RC_OK) { 973 | return rc; 974 | } 975 | 976 | rc = kx13x_set_adp_rms_avg(dev, cfg->rms_avg); 977 | if (rc != KX13X_RC_OK) { 978 | return rc; 979 | } 980 | 981 | /* enabled/disabled ADP engine */ 982 | rc = kx13x_set_adp_enabled(dev, cfg->adp_enabled); 983 | 984 | return rc; 985 | } 986 | 987 | int kx13x_get_adp_data_raw(struct kx13x *dev, int16_t *xyz_raw) 988 | { 989 | int rc; 990 | uint8_t xyz[6]; 991 | 992 | rc = kx13x_read_reg(dev, KX132_1211_XADP_L, (uint8_t*)xyz, 6); 993 | if (rc != KX13X_RC_OK) 994 | { 995 | return rc; 996 | } 997 | 998 | xyz_raw[0] = ((int16_t)xyz[0]) | (((int16_t)xyz[1]) << 8); 999 | xyz_raw[1] = ((int16_t)xyz[2]) | (((int16_t)xyz[3]) << 8); 1000 | xyz_raw[2] = ((int16_t)xyz[4]) | (((int16_t)xyz[5]) << 8); 1001 | 1002 | return KX13X_RC_OK; 1003 | } 1004 | 1005 | int kx13x_get_adp_data(struct kx13x *dev, float *xyz) 1006 | { 1007 | int16_t raw_xyz[3]; 1008 | int rc; 1009 | 1010 | rc = kx13x_get_adp_data_raw(dev, &raw_xyz[0]); 1011 | if (rc != KX13X_RC_OK) 1012 | { 1013 | return rc; 1014 | } 1015 | 1016 | xyz[0] = (float)raw_xyz[0] / dev->gsens; 1017 | xyz[1] = (float)raw_xyz[1] / dev->gsens; 1018 | xyz[2] = (float)raw_xyz[2] / dev->gsens; 1019 | 1020 | return KX13X_RC_OK; 1021 | } 1022 | 1023 | /* Interrupt pin regs */ 1024 | struct kx13x_int_regs { 1025 | uint8_t ctrl; 1026 | uint8_t route; 1027 | }; 1028 | 1029 | static struct kx13x_int_regs int_reg[] = 1030 | { 1031 | /* PIN1 */ 1032 | { 1033 | .ctrl = KX132_1211_INC1, 1034 | .route = KX132_1211_INC4, 1035 | }, 1036 | /* PIN2 */ 1037 | { 1038 | .ctrl = KX132_1211_INC5, 1039 | .route = KX132_1211_INC6, 1040 | }, 1041 | }; 1042 | 1043 | int kx13x_set_int_route(struct kx13x *dev, uint8_t pin, uint8_t route) 1044 | { 1045 | int rc; 1046 | uint8_t reg_val; 1047 | 1048 | if (pin < KX13X_INT1_PIN || pin > KX13X_INT2_PIN) { 1049 | return KX13X_RC_INVALID_PARAM; 1050 | } 1051 | 1052 | reg_val = route; 1053 | 1054 | /* Update all bits in register */ 1055 | rc = kx13x_write_reg_byte(dev, int_reg[pin].route, reg_val); 1056 | if (rc != KX13X_RC_OK) { 1057 | return rc; 1058 | } 1059 | 1060 | return KX13X_RC_OK; 1061 | } 1062 | 1063 | int kx13x_set_int_level(struct kx13x *dev, uint8_t pin, uint8_t level) 1064 | { 1065 | int rc; 1066 | 1067 | if (pin < KX13X_INT1_PIN || pin > KX13X_INT2_PIN) { 1068 | return KX13X_RC_INVALID_PARAM; 1069 | } 1070 | 1071 | switch(level) { 1072 | case KX13X_INT_LEVEL_HIGH: 1073 | rc = kx13x_set_reg_bit(dev, int_reg[pin].ctrl, KX132_1211_INC1_IEA1); 1074 | break; 1075 | case KX13X_INT_LEVEL_LOW: 1076 | rc = kx13x_reset_reg_bit(dev, int_reg[pin].ctrl, KX132_1211_INC1_IEA1); 1077 | break; 1078 | default: 1079 | rc = KX13X_RC_INVALID_PARAM; 1080 | break; 1081 | } 1082 | 1083 | return rc; 1084 | } 1085 | 1086 | static struct kx13x_define_reg_map int_ctrl_map = 1087 | { 1088 | .reg = 0x00, /* not used, reg is get using int_reg */ 1089 | .mask = KX132_1211_INC1_PW1_MASK | KX132_1211_INC1_IEL1, 1090 | .amount = KX13X_INT_CTRL_AMOUNT, 1091 | .values = { 1092 | { 1093 | ._define = KX13X_INT_CTRL_LATCH, 1094 | ._reg_bits = 0x00, 1095 | }, 1096 | { 1097 | ._define = KX13X_INT_CTRL_PULSE_50US_10US, 1098 | ._reg_bits = KX132_1211_INC1_IEL1, 1099 | }, 1100 | { 1101 | ._define = KX13X_INT_CTRL_PULSE_1XODR, 1102 | ._reg_bits = KX132_1211_INC5_PW2_1XODR | KX132_1211_INC1_IEL1, 1103 | }, 1104 | { 1105 | ._define = KX13X_INT_CTRL_PULSE_2XODR, 1106 | ._reg_bits = KX132_1211_INC5_PW2_2XODR | KX132_1211_INC1_IEL1, 1107 | }, 1108 | { 1109 | ._define = KX13X_INT_CTRL_PULSE_REALTIME, 1110 | ._reg_bits = KX132_1211_INC5_PW2_4XODR | KX132_1211_INC1_IEL1, 1111 | }, 1112 | } 1113 | }; 1114 | 1115 | int kx13x_set_int_ctrl(struct kx13x *dev, uint8_t pin, uint8_t ctrl) 1116 | { 1117 | int rc; 1118 | uint8_t reg_bits; 1119 | 1120 | if (pin < KX13X_INT1_PIN || pin > KX13X_INT2_PIN) { 1121 | return KX13X_RC_INVALID_PARAM; 1122 | } 1123 | 1124 | rc = kx13x_map_to_reg_bits(&int_ctrl_map, ctrl, ®_bits); 1125 | if (rc != KX13X_RC_OK) { 1126 | return rc; 1127 | } 1128 | 1129 | rc = kx13x_set_reg_bit_pattern(dev, int_reg[pin].ctrl, reg_bits, int_ctrl_map.mask); 1130 | if (rc != KX13X_RC_OK) { 1131 | return rc; 1132 | } 1133 | 1134 | return KX13X_RC_OK; 1135 | } 1136 | 1137 | int kx13x_set_int_enabled(struct kx13x *dev, uint8_t pin, uint8_t enable) 1138 | { 1139 | int rc; 1140 | 1141 | if (pin < KX13X_INT1_PIN || pin > KX13X_INT2_PIN) { 1142 | return KX13X_RC_INVALID_PARAM; 1143 | } 1144 | 1145 | switch(enable) { 1146 | case KX13X_ENABLED: 1147 | rc = kx13x_set_reg_bit(dev, int_reg[pin].ctrl, KX132_1211_INC1_IEN1); 1148 | break; 1149 | case KX13X_DISABLED: 1150 | rc = kx13x_reset_reg_bit(dev, int_reg[pin].ctrl, KX132_1211_INC1_IEN1); 1151 | break; 1152 | default: 1153 | rc = KX13X_RC_INVALID_PARAM; 1154 | break; 1155 | } 1156 | 1157 | return rc; 1158 | } 1159 | 1160 | int kx13x_set_int_cfg(struct kx13x *dev, uint8_t pin, struct kx13x_interrupt_cfg *cfg) 1161 | { 1162 | int rc; 1163 | 1164 | if (pin < KX13X_INT1_PIN || pin > KX13X_INT2_PIN) { 1165 | return KX13X_RC_INVALID_PARAM; 1166 | } 1167 | 1168 | rc = kx13x_set_int_route(dev, pin, cfg->routing); 1169 | if (rc != KX13X_RC_OK) { 1170 | return rc; 1171 | } 1172 | 1173 | rc = kx13x_set_int_level(dev, pin, cfg->level); 1174 | if (rc != KX13X_RC_OK) { 1175 | return rc; 1176 | } 1177 | 1178 | rc = kx13x_set_int_ctrl(dev, pin, cfg->ctrl); 1179 | if (rc != KX13X_RC_OK) { 1180 | return rc; 1181 | } 1182 | 1183 | rc = kx13x_set_int_enabled(dev, pin, cfg->enable); 1184 | if (rc != KX13X_RC_OK) { 1185 | return rc; 1186 | } 1187 | 1188 | return KX13X_RC_OK; 1189 | } 1190 | 1191 | int kx13x_get_int_status(struct kx13x *dev, uint8_t *status) 1192 | { 1193 | int rc; 1194 | rc = kx13x_read_reg_byte(dev, KX132_1211_STATUS_REG, status); 1195 | return rc; 1196 | } 1197 | 1198 | int kx13x_get_int_ins123(struct kx13x *dev, uint8_t *ins123) 1199 | { 1200 | int rc; 1201 | rc = kx13x_read_reg(dev, KX132_1211_INS1, ins123, 3); 1202 | return rc; 1203 | } 1204 | 1205 | /* */ 1206 | int kx13x_release_int(struct kx13x *dev) 1207 | { 1208 | int rc; 1209 | uint8_t dummy; 1210 | 1211 | rc = kx13x_read_reg_byte(dev, KX132_1211_INT_REL, &dummy); 1212 | 1213 | return rc; 1214 | } 1215 | 1216 | /* */ 1217 | int kx13x_reset(struct kx13x *dev) 1218 | { 1219 | int rc; 1220 | 1221 | rc = kx13x_set_reg_bit(dev, KX132_1211_CNTL2, KX132_1211_CNTL2_SRST); 1222 | if (rc != KX13X_RC_OK) { 1223 | return rc; 1224 | } 1225 | 1226 | (void)kx13x_platform_delay_ms(dev->plat, 10); 1227 | 1228 | return KX13X_RC_OK; 1229 | } 1230 | 1231 | /* */ 1232 | int kx13x_verify_who_am_i_id(struct kx13x *dev, uint8_t* wai_id) 1233 | { 1234 | struct kx13x_sensor_info *sensor; 1235 | int rc; 1236 | uint8_t reg_val; 1237 | 1238 | rc = kx13x_read_reg_byte(dev, KX132_1211_WHO_AM_I, ®_val); 1239 | if (rc != KX13X_RC_OK) { 1240 | return rc; 1241 | } 1242 | 1243 | /* check if sensor is supported */ 1244 | sensor = kx13x_sensors_info_is_supported(reg_val); 1245 | if (sensor) { 1246 | KX13X_TRACE_STR_1(dev, "kx13x sensor supported type %d\n", sensor->type); 1247 | *wai_id = sensor->wai_id; 1248 | } else { 1249 | rc = KX13X_RC_NOT_SUPPORTED; 1250 | } 1251 | 1252 | return rc; 1253 | } 1254 | 1255 | /* */ 1256 | int kx13x_init(struct kx13x *dev, struct platform *plat) 1257 | { 1258 | int rc; 1259 | uint8_t wai_id = 0; 1260 | 1261 | /* platform data */ 1262 | dev->plat = plat; 1263 | 1264 | KX13X_TRACE_STR(dev, "kx13x_init\n"); 1265 | 1266 | rc = kx13x_verify_who_am_i_id(dev, &wai_id); 1267 | if (rc != KX13X_RC_OK) { 1268 | return rc; 1269 | } 1270 | dev->wai_id = wai_id; 1271 | 1272 | KX13X_TRACE_STR_1(dev, "kx13x wai_id %d\n", dev->wai_id); 1273 | 1274 | rc = kx13x_reset(dev); 1275 | if (rc != KX13X_RC_OK) { 1276 | return rc; 1277 | } 1278 | 1279 | /* set default values */ 1280 | { 1281 | struct kx13x_sensor_info *sensor = NULL; 1282 | /* get sensor info */ 1283 | sensor = kx13x_sensors_info_is_supported(dev->wai_id); 1284 | if (sensor == NULL) { 1285 | return KX13X_RC_ERR; 1286 | } 1287 | dev->granges = sensor->granges; 1288 | 1289 | if (dev->granges & KX13X_GRANGE_64G) { 1290 | dev->gsens = KX13X_GRANGE_TO_GSENS(KX13X_GRANGE_16G); 1291 | } else { 1292 | dev->gsens = KX13X_GRANGE_TO_GSENS(KX13X_GRANGE_2G); 1293 | } 1294 | } 1295 | 1296 | KX13X_TRACE_STR(dev, "kx13x_init exit\n"); 1297 | 1298 | return KX13X_RC_OK; 1299 | } 1300 | 1301 | char* kx13x_get_name(struct kx13x *dev) 1302 | { 1303 | struct kx13x_sensor_info *sensor = NULL; 1304 | 1305 | /* get sensor info */ 1306 | sensor = kx13x_sensors_info_is_supported(dev->wai_id); 1307 | if (sensor) { 1308 | return sensor->name; 1309 | } 1310 | 1311 | return NULL; 1312 | } 1313 | 1314 | int kx13x_set_config(struct kx13x *dev, struct kx13x_cfg *cfg) 1315 | { 1316 | int rc; 1317 | 1318 | if (cfg->accel) { 1319 | rc = kx13x_set_accel_cfg(dev, cfg->accel); 1320 | if (rc != KX13X_RC_OK) { 1321 | return rc; 1322 | } 1323 | } 1324 | 1325 | if (cfg->wu_bts) { 1326 | rc = kx13x_set_wu_bts_cfg(dev, cfg->wu_bts); 1327 | if (rc != KX13X_RC_OK) { 1328 | return rc; 1329 | } 1330 | } 1331 | 1332 | if (cfg->adp) { 1333 | rc = kx13x_set_adp_cfg(dev, cfg->adp); 1334 | if (rc != KX13X_RC_OK) { 1335 | return rc; 1336 | } 1337 | } 1338 | 1339 | if (cfg->int1) { 1340 | rc = kx13x_set_int_cfg(dev, KX13X_INT1_PIN, cfg->int1); 1341 | if (rc != KX13X_RC_OK) { 1342 | return rc; 1343 | } 1344 | } 1345 | 1346 | if (cfg->int2) { 1347 | rc = kx13x_set_int_cfg(dev, KX13X_INT2_PIN, cfg->int2); 1348 | if (rc != KX13X_RC_OK) { 1349 | return rc; 1350 | } 1351 | } 1352 | 1353 | rc = kx13x_set_oper_mode(dev, cfg->oper_mode); 1354 | if (rc != KX13X_RC_OK) { 1355 | return rc; 1356 | } 1357 | 1358 | return KX13X_RC_OK; 1359 | } 1360 | -------------------------------------------------------------------------------- /kx13x/kx13x.h: -------------------------------------------------------------------------------- 1 | /* 2 | The MIT License (MIT) 3 | Copyright (c) 2020 ROHM Co.,Ltd. 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a 6 | copy of this software and associated documentation files (the 7 | "Software"), to deal in the Software without restriction, including 8 | without limitation the rights to use, copy, modify, merge, publish, 9 | distribute, sublicense, and/or sell copies of the Software, and to 10 | permit persons to whom the Software is furnished to do so, subject to 11 | the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included 14 | in all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 17 | OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 18 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 19 | IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY 20 | CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 21 | TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 22 | SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 23 | */ 24 | 25 | #ifndef __KX13X_H__ 26 | #define __KX13X_H__ 27 | 28 | #ifdef __cplusplus 29 | extern "C" { 30 | #endif 31 | 32 | /* I2C address */ 33 | #define KX13X_I2C_ADDRESS_1E (0x1E) 34 | #define KX13X_I2C_ADDRESS_1F (0x1F) 35 | 36 | /* supported sensors */ 37 | #define KX13X_TYPE_KX132_1211 1 38 | #define KX13X_TYPE_KX134_1211 2 39 | 40 | /* sensor feature, bit */ 41 | #define KX13X_FEA_NONE 0x00 42 | #define KX13X_FEA_DRDY (0x01 << 0) 43 | #define KX13X_FEA_BUF (0x01 << 2) 44 | #define KX13X_FEA_WUF (0x01 << 3) 45 | #define KX13X_FEA_BTS (0x01 << 4) 46 | #define KX13X_FEA_FREEFALL (0x01 << 5) 47 | #define KX13X_FEA_TAP (0x01 << 6) 48 | #define KX13X_FEA_TILT (0x01 << 7) 49 | 50 | /* forward declare */ 51 | struct kx13x; 52 | struct platform; 53 | 54 | /* Function return codes */ 55 | #define KX13X_RC_OK (0) 56 | #define KX13X_RC_ERR (-1) 57 | #define KX13X_RC_INVALID_PARAM (-2) 58 | #define KX13X_RC_NOT_SUPPORTED (-3) 59 | 60 | /* KX13x disabled/enabled feature */ 61 | #define KX13X_DISABLED 0 62 | #define KX13X_ENABLED 1 63 | 64 | /* KX13X operating modes */ 65 | #define KX13X_OPER_MODE_STANDBY 0 66 | #define KX13X_OPER_MODE_OPERATING 1 67 | int kx13x_set_oper_mode(struct kx13x *dev, uint8_t mode); 68 | int kx13x_get_oper_mode(struct kx13x *dev, uint8_t *mode); 69 | 70 | /* KX13X performance mode */ 71 | #define KX13X_PERF_MODE_LOW_POWER 0 72 | #define KX13X_PERF_MODE_HIGH_RES 1 73 | int kx13x_set_perf_mode(struct kx13x *dev, uint8_t mode); 74 | 75 | /* KX13X acceleration range, bits */ 76 | #define KX13X_GRANGE_2G 2 77 | #define KX13X_GRANGE_4G 4 78 | #define KX13X_GRANGE_8G 8 79 | #define KX13X_GRANGE_16G 16 80 | #define KX13X_GRANGE_32G 32 81 | #define KX13X_GRANGE_64G 64 82 | #define KX13X_GRANGE_AMOUNT 6 83 | int kx13x_set_grange(struct kx13x *dev, uint8_t grange); 84 | 85 | /* KX13X ODR */ 86 | #define KX13X_ODR_0P781HZ (0x00 << 0) 87 | #define KX13X_ODR_1P563HZ (0x01 << 0) 88 | #define KX13X_ODR_3P125HZ (0x02 << 0) 89 | #define KX13X_ODR_6P25HZ (0x03 << 0) 90 | #define KX13X_ODR_12P5HZ (0x04 << 0) 91 | #define KX13X_ODR_25HZ (0x05 << 0) 92 | #define KX13X_ODR_50HZ (0x06 << 0) 93 | #define KX13X_ODR_100HZ (0x07 << 0) 94 | #define KX13X_ODR_200HZ (0x08 << 0) 95 | #define KX13X_ODR_400HZ (0x09 << 0) 96 | #define KX13X_ODR_800HZ (0x0A << 0) 97 | #define KX13X_ODR_1600HZ (0x0B << 0) 98 | #define KX13X_ODR_3200HZ (0x0C << 0) 99 | #define KX13X_ODR_6400HZ (0x0D << 0) 100 | #define KX13X_ODR_12800HZ (0x0E << 0) 101 | #define KX13X_ODR_25600HZ (0x0F << 0) 102 | int kx13x_set_odr(struct kx13x *dev, uint8_t odr); 103 | 104 | /* KX13x disable/enable DRDY */ 105 | int kx13x_set_drdy_enabled(struct kx13x *dev, uint8_t enable); 106 | 107 | /* KX13X low pass filter */ 108 | #define KX13X_BYPASS_ODR_2 0 109 | #define KX13X_BYPASS_ODR_9 1 110 | #define KX13X_BYPASS_AMOUNT 2 111 | int kx13x_set_low_pass_filter(struct kx13x *dev, uint8_t filter); 112 | 113 | /* KX13X avg filter */ 114 | #define KX13X_AVG_NO_AVG 0 115 | #define KX13X_AVG_2_SAMPLE 1 116 | #define KX13X_AVG_4_SAMPLE 2 117 | #define KX13X_AVG_8_SAMPLE 3 118 | #define KX13X_AVG_16_SAMPLE 4 119 | #define KX13X_AVG_32_SAMPLE 5 120 | #define KX13X_AVG_64_SAMPLE 6 121 | #define KX13X_AVG_AMOUNT 7 122 | int kx13x_set_avg_filter_ctrl(struct kx13x *dev, uint8_t avc); 123 | 124 | /* KX13X accel config structure */ 125 | struct kx13x_accel_cfg { 126 | uint8_t perf_mode; 127 | uint8_t grange; 128 | uint8_t odr; 129 | uint8_t drdy_enable; 130 | uint8_t filter; 131 | uint8_t avc; /* Note, affects also to other engines */ 132 | }; 133 | 134 | int kx13x_set_accel_cfg(struct kx13x *dev, struct kx13x_accel_cfg *cfg); 135 | 136 | /* KX13X get accel xyz-data */ 137 | int kx13x_get_accel_data_raw(struct kx13x *dev, int16_t *xyz_raw); 138 | int kx13x_get_accel_data(struct kx13x *dev, float *xyz); 139 | 140 | /* KX13X Wake-up/back to sleep feature */ 141 | 142 | /* KX13X wu or bts odr */ 143 | #define KX13X_WU_0P781HZ 0x00 144 | #define KX13X_WU_1P563HZ 0x01 145 | #define KX13X_WU_3P125HZ 0x02 146 | #define KX13X_WU_6P25HZ 0x03 147 | #define KX13X_WU_12P5HZ 0x04 148 | #define KX13X_WU_25HZ 0x05 149 | #define KX13X_WU_50HZ 0x06 150 | #define KX13X_WU_100HZ 0x07 151 | 152 | /* KX13X wu or bts config struct */ 153 | struct kx13x_wu_cfg { 154 | uint8_t enable; /* wakeup/back-to-sleep enabled */ 155 | uint16_t threshold; /* 3.9 mg/count, 11bit value */ 156 | uint8_t counter; /* WUFC/BTSC counter */ 157 | uint8_t odr; /* WU/BTS counter */ 158 | }; 159 | 160 | /* KX13X wu/bts modes */ 161 | #define KX13X_WU_MODES_C_RESET (0x00 << 7) 162 | #define KX13X_WU_MODES_C_DECREMENTED (0x01 << 7) 163 | #define KX13X_WU_MODES_TH_ABSOLUTE (0x00 << 6) 164 | #define KX13X_WU_MODES_TH_RELATIVE (0x01 << 6) 165 | #define KX13X_WU_MODES_PR_STANDARD (0x00 << 3) 166 | #define KX13X_WU_MODES_PR_REJECTED (0x01 << 3) 167 | 168 | /* KX13X wu/bts axes config */ 169 | #define KX13X_WU_AXES_AOI_OR (0x00 << 6) 170 | #define KX13X_WU_AXES_AOI_AND (0x01 << 6) 171 | #define KX13X_WU_AXES_XNWUE (0x01 << 5) 172 | #define KX13X_WU_AXES_XPWUE (0x01 << 4) 173 | #define KX13X_WU_AXES_YNWUE (0x01 << 3) 174 | #define KX13X_WU_AXES_YPWUE (0x01 << 2) 175 | #define KX13X_WU_AXES_ZNWUE (0x01 << 1) 176 | #define KX13X_WU_AXES_ZPWUE (0x01 << 0) 177 | 178 | /* KX13X wu/bts config */ 179 | struct kx13x_wu_bts_cfg { 180 | struct kx13x_wu_cfg *wu; /* wake-up config or NULL */ 181 | struct kx13x_wu_cfg *bts; /* back-to-sleep config or NULL */ 182 | uint8_t mode_bits; /* common config */ 183 | uint8_t axes_bits; /* common config */ 184 | }; 185 | 186 | int kx13x_set_wu_bts_cfg(struct kx13x *dev, struct kx13x_wu_bts_cfg *cfg); 187 | 188 | /* KX13X ADP config */ 189 | 190 | /* ADP filter1 */ 191 | #define KX13X_ADP_FILTER1_NONE (0xff) 192 | #define KX13X_ADP_FILTER1_LP_ODR_4 (0) 193 | #define KX13X_ADP_FILTER1_LP_ODR_8 (1) 194 | #define KX13X_ADP_FILTER1_LP_ODR_16 (2) 195 | #define KX13X_ADP_FILTER1_LP_ODR_32 (3) 196 | #define KX13X_ADP_FILTER1_LP_ODR_64 (4) 197 | #define KX13X_ADP_FILTER1_LP_ODR_128 (5) 198 | #define KX13X_ADP_FILTER1_LP_ODR_256 (6) 199 | #define KX13X_ADP_FILTER1_LP_ODR_512 (7) 200 | #define KX13X_ADP_FILTER1_LP_ODR_1024 (8) 201 | #define KX13X_ADP_FILTER1_LP_ODR_2048 (9) 202 | #define KX13X_ADP_FILTER1_LP_ODR_6p400 (10) 203 | #define KX13X_ADP_FILTER1_LP_ODR_4p266 (11) 204 | #define KX13X_ADP_FILTER1_LP_ODR_4p830 (12) 205 | 206 | /* ADP filter2 */ 207 | #define KX13X_ADP_FILTER2_NONE (0xff) 208 | /* LP-filters */ 209 | #define KX13X_ADP_FILTER2_LP_ODR_4 (0) 210 | #define KX13X_ADP_FILTER2_LP_ODR_8 (1) 211 | #define KX13X_ADP_FILTER2_LP_ODR_16 (2) 212 | #define KX13X_ADP_FILTER2_LP_ODR_32 (3) 213 | #define KX13X_ADP_FILTER2_LP_ODR_64 (4) 214 | #define KX13X_ADP_FILTER2_LP_ODR_128 (5) 215 | #define KX13X_ADP_FILTER2_LP_ODR_256 (6) 216 | #define KX13X_ADP_FILTER2_LP_ODR_512 (7) 217 | #define KX13X_ADP_FILTER2_LP_ODR_1024 (8) 218 | #define KX13X_ADP_FILTER2_LP_ODR_2048 (9) 219 | #define KX13X_ADP_FILTER2_LP_ODR_8p533 (10) 220 | /* HP-filters */ 221 | #define KX13X_ADP_FILTER2_HP_ODR_4 (11) 222 | #define KX13X_ADP_FILTER2_HP_ODR_8 (12) 223 | #define KX13X_ADP_FILTER2_HP_ODR_16 (13) 224 | #define KX13X_ADP_FILTER2_HP_ODR_32 (14) 225 | #define KX13X_ADP_FILTER2_HP_ODR_40 (15) 226 | #define KX13X_ADP_FILTER2_HP_ODR_64 (16) 227 | #define KX13X_ADP_FILTER2_HP_ODR_128 (17) 228 | #define KX13X_ADP_FILTER2_HP_ODR_256 (18) 229 | #define KX13X_ADP_FILTER2_HP_ODR_512 (19) 230 | #define KX13X_ADP_FILTER2_HP_ODR_640 (20) 231 | #define KX13X_ADP_FILTER2_HP_ODR_1024 (21) 232 | #define KX13X_ADP_FILTER2_HP_ODR_2048 (22) 233 | #define KX13X_ADP_FILTER2_HP_ODR_6p400 (23) 234 | #define KX13X_ADP_FILTER2_HP_ODR_4p413 (24) 235 | #define KX13X_ADP_FILTER2_HP_ODR_4p266 (25) 236 | #define KX13X_ADP_FILTER2_HP_ODR_2p844 (26) 237 | #define KX13X_ADP_FILTER2_HP_ODR_3p938 (27) 238 | /* HP-filters start index */ 239 | #define KX13X_ADP_FILTER2_HP_FILTERS KX13X_ADP_FILTER2_HP_ODR_4 240 | 241 | /* ADP RMS average */ 242 | #define KX13X_ADP_RMS_AVC_NONE (0xff) 243 | #define KX13X_ADP_RMS_AVC_2_SAMPLE_AVG (0x00 << 4) 244 | #define KX13X_ADP_RMS_AVC_4_SAMPLE_AVG (0x01 << 4) 245 | #define KX13X_ADP_RMS_AVC_8_SAMPLE_AVG (0x02 << 4) 246 | #define KX13X_ADP_RMS_AVC_16_SAMPLE_AVG (0x03 << 4) 247 | #define KX13X_ADP_RMS_AVC_32_SAMPLE_AVG (0x04 << 4) 248 | #define KX13X_ADP_RMS_AVC_64_SAMPLE_AVG (0x05 << 4) 249 | #define KX13X_ADP_RMS_AVC_128_SAMPLE_AVG (0x06 << 4) 250 | #define KX13X_ADP_RMS_AVC_256_SAMPLE_AVG (0x07 << 4) 251 | 252 | /* ADP engine configuration */ 253 | struct kx13x_adp_cfg { 254 | uint8_t filter1; /* KX13X_ADP_FILTER1_ */ 255 | uint8_t filter2; /* KX13X_ADP_FILTER2_ */ 256 | uint8_t adp_odr; /* KX132X_ODR_ */ 257 | uint8_t rms_avg; /* KX13X_ADP_RMS_AVC_ */ 258 | uint8_t adp_enabled; /* KX13X_DISABLED / KX13X_ENABLED */ 259 | }; 260 | 261 | int kx13x_set_adp_cfg(struct kx13x *dev, struct kx13x_adp_cfg *cfg); 262 | 263 | int kx13x_get_adp_data_raw(struct kx13x *dev, int16_t *xyz_raw); 264 | int kx13x_get_adp_data(struct kx13x *dev, float *xyz); 265 | 266 | /* KX13X interrupt */ 267 | 268 | /* KX13X int pin selection */ 269 | #define KX13X_INT1_PIN 0 270 | #define KX13X_INT2_PIN 1 271 | 272 | /* KX13X interrupt routing bits */ 273 | #define KX13X_INT_ROUTE_NONE 0x00 274 | #define KX13X_INT_ROUTE_TILT (0x01 << 0) 275 | #define KX13X_INT_ROUTE_WUF (0x01 << 1) 276 | #define KX13X_INT_ROUTE_TAP (0x01 << 2) 277 | #define KX13X_INT_ROUTE_BTS (0x01 << 3) 278 | #define KX13X_INT_ROUTE_DRDY (0x01 << 4) 279 | #define KX13X_INT_ROUTE_BUF_WM (0x01 << 5) 280 | #define KX13X_INT_ROUTE_BUF_FULL (0x01 << 6) 281 | #define KX13X_INT_ROUTE_FREEFALL (0x01 << 7) 282 | int kx13x_set_int_route(struct kx13x *dev, uint8_t pin, uint8_t route); 283 | 284 | /* KX13X interrupt level */ 285 | #define KX13X_INT_LEVEL_LOW 0 286 | #define KX13X_INT_LEVEL_HIGH 1 287 | int kx13x_set_int_level(struct kx13x *dev, uint8_t pin, uint8_t level); 288 | 289 | /* KX13X interrupt control */ 290 | #define KX13X_INT_CTRL_LATCH 0 291 | #define KX13X_INT_CTRL_PULSE_50US_10US 1 292 | #define KX13X_INT_CTRL_PULSE_1XODR 2 293 | #define KX13X_INT_CTRL_PULSE_2XODR 3 294 | #define KX13X_INT_CTRL_PULSE_REALTIME 4 295 | #define KX13X_INT_CTRL_AMOUNT 5 296 | int kx13x_set_int_ctrl(struct kx13x *dev, uint8_t pin, uint8_t int_ctrl); 297 | 298 | /* KX13X interrupt pin enable/disable */ 299 | int kx13x_set_int_enabled(struct kx13x *dev, uint8_t pin, uint8_t enable); 300 | 301 | /* KX13X interrupt pin config */ 302 | struct kx13x_interrupt_cfg { 303 | uint8_t enable; 304 | uint8_t routing; 305 | uint8_t level; 306 | uint8_t ctrl; 307 | }; 308 | 309 | int kx13x_set_int_cfg(struct kx13x *dev, uint8_t pin, struct kx13x_interrupt_cfg *cfg); 310 | 311 | /* Interrupt statuses */ 312 | #define KX13X_INT_STATUS_OCCURED (0x01 << 4) 313 | int kx13x_get_int_status(struct kx13x *dev, uint8_t *status); 314 | 315 | /* INS2 status */ 316 | #define KX13X_INT_INS2_DRDY (0x01 << 4) 317 | /* INS3 status */ 318 | #define KX13X_INT_INS3_BTS (0x01 << 6) 319 | #define KX13X_INT_INS3_WUFS (0x01 << 7) 320 | int kx13x_get_int_ins123(struct kx13x *dev, uint8_t *ins123); 321 | 322 | /* KX13X interrupt latch */ 323 | int kx13x_release_int(struct kx13x *dev); 324 | 325 | /* KX13X soft reset */ 326 | int kx13x_reset(struct kx13x *dev); 327 | 328 | /* Sensor configuration structure */ 329 | struct kx13x_cfg { 330 | uint8_t oper_mode; /* mandatory */ 331 | struct kx13x_accel_cfg *accel; /* cfg or NULL */ 332 | struct kx13x_wu_bts_cfg *wu_bts; /* cfg or NULL */ 333 | struct kx13x_adp_cfg *adp; /* cfg or NULL */ 334 | struct kx13x_interrupt_cfg *int1; /* cfg or NULL */ 335 | struct kx13x_interrupt_cfg *int2; /* cfg or NULL */ 336 | }; 337 | 338 | /* Sensor driver data structure */ 339 | struct kx13x { 340 | struct platform *plat; /* data provided by platform */ 341 | uint16_t granges; /* supported granges */ 342 | uint16_t gsens; /* accel raw data to si-format convert param */ 343 | uint8_t wai_id; /* wai_id read from sensor */ 344 | }; 345 | 346 | /** 347 | * 348 | */ 349 | int kx13x_init(struct kx13x *dev, struct platform *plat); 350 | 351 | /** 352 | * Returns pointer to sensor name or NULL in fail case 353 | */ 354 | char* kx13x_get_name(struct kx13x *dev); 355 | 356 | /** 357 | * Sets sensor device configuration. 358 | * 359 | * @param dev Pointer to the kx13x struct 360 | * @param dev_cfg Pointer to the kx13x configuration 361 | * 362 | * @return 0 on success, non-zero on failure. 363 | */ 364 | int kx13x_set_config(struct kx13x *dev, struct kx13x_cfg *dev_cfg); 365 | 366 | /** 367 | * Dump sensor registers 368 | */ 369 | int kx13x_debug_dump_regs(struct kx13x *dev); 370 | 371 | #ifdef __cplusplus 372 | } 373 | #endif 374 | 375 | #endif /* __KX13X_H__ */ 376 | -------------------------------------------------------------------------------- /kx13x/kx13x_example.c: -------------------------------------------------------------------------------- 1 | /* 2 | The MIT License (MIT) 3 | Copyright (c) 2020 ROHM Co.,Ltd. 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a 6 | copy of this software and associated documentation files (the 7 | "Software"), to deal in the Software without restriction, including 8 | without limitation the rights to use, copy, modify, merge, publish, 9 | distribute, sublicense, and/or sell copies of the Software, and to 10 | permit persons to whom the Software is furnished to do so, subject to 11 | the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included 14 | in all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 17 | OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 18 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 19 | IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY 20 | CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 21 | TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 22 | SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 23 | */ 24 | 25 | #include 26 | #include 27 | #include 28 | 29 | #include "platform.h" 30 | #include "kx13x.h" 31 | #include "kx13x_example.h" 32 | 33 | #define UNUSED_VAR(a) (void)a 34 | 35 | /* Sensor main config */ 36 | struct kx13x_cfg main_cfg; 37 | 38 | /* Sensor feature configs */ 39 | struct kx13x_accel_cfg accel; 40 | struct kx13x_wu_bts_cfg wu_bts_cfg; 41 | struct kx13x_wu_cfg wu_cfg; 42 | struct kx13x_wu_cfg bts_cfg; 43 | struct kx13x_adp_cfg adp_cfg; 44 | struct kx13x_interrupt_cfg int1; 45 | struct kx13x_interrupt_cfg int2; 46 | 47 | /* KX13X_EXAMPLE_DRDY_POLL */ 48 | static struct kx13x_cfg *kx13x_ex_get_drdy_poll_cfg(struct kx13x *dev) 49 | { 50 | /* Fill accel */ 51 | accel.perf_mode = KX13X_PERF_MODE_HIGH_RES; 52 | if (dev->granges & KX13X_GRANGE_64G) { 53 | // kx134: 8,16,32,64 54 | accel.grange = KX13X_GRANGE_8G; 55 | } else { 56 | // kx132: 2,4,8,16 57 | accel.grange = KX13X_GRANGE_2G; 58 | } 59 | 60 | accel.odr = KX13X_ODR_3P125HZ; 61 | accel.drdy_enable = KX13X_ENABLED; 62 | accel.filter = KX13X_BYPASS_ODR_9; 63 | accel.avc = KX13X_AVG_4_SAMPLE; 64 | 65 | /* Add all configs to main config */ 66 | main_cfg.oper_mode = KX13X_OPER_MODE_STANDBY; 67 | main_cfg.accel = &accel; 68 | main_cfg.wu_bts = NULL; 69 | main_cfg.adp = NULL; 70 | main_cfg.int1 = NULL; 71 | main_cfg.int2 = NULL; 72 | 73 | return &main_cfg; 74 | } 75 | 76 | /* KX13X_EXAMPLE_DRDY_INTERRUPT */ 77 | static struct kx13x_cfg *kx13x_ex_get_drdy_interrupt_cfg(struct kx13x *dev) 78 | { 79 | /* Fill accel */ 80 | accel.perf_mode = KX13X_PERF_MODE_HIGH_RES; 81 | if (dev->granges & KX13X_GRANGE_64G) { 82 | // kx134: 8,16,32,64 83 | accel.grange = KX13X_GRANGE_8G; 84 | } else { 85 | // kx132: 2,4,8,16 86 | accel.grange = KX13X_GRANGE_2G; 87 | } 88 | 89 | accel.odr = KX13X_ODR_3P125HZ; 90 | accel.drdy_enable = KX13X_ENABLED; 91 | accel.filter = KX13X_BYPASS_ODR_9; 92 | accel.avc = KX13X_AVG_4_SAMPLE; 93 | 94 | /* Fill interrupt pin1 config */ 95 | int1.enable = KX13X_ENABLED; 96 | int1.routing = KX13X_INT_ROUTE_DRDY; 97 | int1.level = KX13X_INT_LEVEL_HIGH; 98 | int1.ctrl = KX13X_INT_CTRL_PULSE_50US_10US; 99 | 100 | /* Add all configs to main config */ 101 | main_cfg.oper_mode = KX13X_OPER_MODE_STANDBY; 102 | main_cfg.accel = &accel; 103 | main_cfg.wu_bts = NULL; 104 | main_cfg.adp = NULL; 105 | main_cfg.int1 = &int1; 106 | main_cfg.int2 = NULL; 107 | 108 | return &main_cfg; 109 | } 110 | 111 | /* KX13X_EXAMPLE_WU_BTS_INTERRUPT */ 112 | static struct kx13x_cfg *kx13x_ex_get_wu_bts_interrupt_cfg(struct kx13x *dev) 113 | { 114 | UNUSED_VAR(dev); 115 | 116 | /* Set wake-up and back to sleep cfg */ 117 | wu_cfg.threshold = 20; /* 3.9mg*value */ 118 | wu_cfg.counter = 2; /* 1/wu_odr*value */ 119 | wu_cfg.odr = KX13X_WU_12P5HZ; 120 | wu_cfg.enable = KX13X_ENABLED; 121 | wu_bts_cfg.wu = &wu_cfg; 122 | 123 | bts_cfg.threshold = 20; /* 3.9mg*value */ 124 | bts_cfg.counter = 2; /* 1/bts_odr*value */ 125 | bts_cfg.odr = KX13X_WU_12P5HZ; 126 | bts_cfg.enable = KX13X_ENABLED; 127 | wu_bts_cfg.bts = &bts_cfg; 128 | 129 | /* set wu/bts common config */ 130 | wu_bts_cfg.mode_bits = KX13X_WU_MODES_PR_STANDARD| 131 | KX13X_WU_MODES_TH_RELATIVE| 132 | KX13X_WU_MODES_C_RESET; 133 | 134 | wu_bts_cfg.axes_bits = KX13X_WU_AXES_AOI_OR | 135 | KX13X_WU_AXES_XNWUE | 136 | KX13X_WU_AXES_XPWUE | 137 | KX13X_WU_AXES_YNWUE | 138 | KX13X_WU_AXES_YPWUE | 139 | KX13X_WU_AXES_ZNWUE | 140 | KX13X_WU_AXES_ZPWUE; 141 | 142 | /* Route wu/bts to int2 pin */ 143 | int2.enable = KX13X_ENABLED; 144 | int2.routing = KX13X_INT_ROUTE_WUF | KX13X_INT_ROUTE_BTS; 145 | int2.level = KX13X_INT_LEVEL_HIGH; 146 | int2.ctrl = KX13X_INT_CTRL_LATCH; 147 | 148 | /* Add all configs to main config */ 149 | main_cfg.oper_mode = KX13X_OPER_MODE_STANDBY; 150 | main_cfg.accel = NULL; 151 | main_cfg.wu_bts = &wu_bts_cfg; 152 | main_cfg.adp = NULL; 153 | main_cfg.int1 = NULL; 154 | main_cfg.int2 = &int2; 155 | 156 | return &main_cfg; 157 | } 158 | 159 | /* KX13X_EXAMPLE_ADP_DATA */ 160 | static struct kx13x_cfg *kx13x_ex_get_adp_data_cfg(struct kx13x *dev) 161 | { 162 | UNUSED_VAR(dev); 163 | 164 | /* Fill accel */ 165 | accel.perf_mode = KX13X_PERF_MODE_HIGH_RES; 166 | if (dev->granges & KX13X_GRANGE_64G) { 167 | // kx134: 8,16,32,64 168 | accel.grange = KX13X_GRANGE_8G; 169 | } else { 170 | // kx132: 2,4,8,16 171 | accel.grange = KX13X_GRANGE_2G; 172 | } 173 | 174 | accel.odr = KX13X_ODR_100HZ; 175 | accel.drdy_enable = KX13X_ENABLED; 176 | accel.filter = KX13X_BYPASS_ODR_2; 177 | accel.avc = KX13X_AVG_2_SAMPLE; 178 | 179 | /* Fill ADP engine config */ 180 | adp_cfg.filter1 = KX13X_ADP_FILTER1_LP_ODR_4; 181 | adp_cfg.filter2 = KX13X_ADP_FILTER2_HP_ODR_8; 182 | adp_cfg.adp_odr = KX13X_ODR_100HZ; 183 | adp_cfg.rms_avg = KX13X_ADP_RMS_AVC_64_SAMPLE_AVG; 184 | adp_cfg.adp_enabled = KX13X_ENABLED; 185 | 186 | /* Add all configs to main config */ 187 | main_cfg.oper_mode = KX13X_OPER_MODE_STANDBY; 188 | main_cfg.accel = &accel; 189 | main_cfg.wu_bts = NULL; 190 | main_cfg.adp = &adp_cfg; 191 | main_cfg.int1 = NULL; 192 | main_cfg.int2 = NULL; 193 | 194 | return &main_cfg; 195 | } 196 | 197 | /* writes new config to sensor, does not set sensor to oper mode*/ 198 | struct kx13x_cfg *kx13x_example_update_config(struct kx13x *dev, uint8_t example) 199 | { 200 | struct kx13x_cfg *cfg; 201 | int rc; 202 | 203 | /* clear previous config */ 204 | rc = kx13x_reset(dev); 205 | if (rc != KX13X_RC_OK) { 206 | return NULL; 207 | } 208 | 209 | /* Dump registers after sensor reset */ 210 | rc = kx13x_debug_dump_regs(dev); 211 | if (rc != KX13X_RC_OK) { 212 | return NULL; 213 | } 214 | 215 | switch (example) { 216 | case KX13X_EXAMPLE_DRDY_POLL: 217 | if (dev->plat->debug_print) { 218 | dev->plat->debug_print(dev->plat,"KX13X_EXAMPLE_DRDY_POLL\n"); 219 | } 220 | cfg = kx13x_ex_get_drdy_poll_cfg(dev); 221 | break; 222 | case KX13X_EXAMPLE_DRDY_INTERRUPT: 223 | if (dev->plat->debug_print) { 224 | dev->plat->debug_print(dev->plat,"KX13X_EXAMPLE_DRDY_INTERRUPT\n"); 225 | } 226 | cfg = kx13x_ex_get_drdy_interrupt_cfg(dev); 227 | break; 228 | case KX13X_EXAMPLE_WU_BTS_INTERRUPT: 229 | if (dev->plat->debug_print) { 230 | dev->plat->debug_print(dev->plat,"KX13X_EXAMPLE_WU_BTS_INTERRUPT\n"); 231 | } 232 | cfg = kx13x_ex_get_wu_bts_interrupt_cfg(dev); 233 | break; 234 | case KX13X_EXAMPLE_ADP_DATA: 235 | if (dev->plat->debug_print) { 236 | dev->plat->debug_print(dev->plat,"KX13X_EXAMPLE_ADP_DATA\n"); 237 | } 238 | cfg = kx13x_ex_get_adp_data_cfg(dev); 239 | break; 240 | default: 241 | return NULL; 242 | break; 243 | } 244 | 245 | rc = kx13x_set_config(dev, cfg); 246 | if (rc != KX13X_RC_OK) { 247 | return NULL; 248 | } 249 | 250 | /* Dump registers after config is written to sensor */ 251 | rc = kx13x_debug_dump_regs(dev); 252 | if (rc != KX13X_RC_OK) { 253 | return NULL; 254 | } 255 | 256 | return cfg; 257 | } 258 | 259 | static int kx13x_example_read_and_print_data(struct kx13x *dev) 260 | { 261 | int rc; 262 | float xyz[3] = {0.0F}; 263 | int xyz_mg[3] = {0}; 264 | int adp_xyz_mg[3] = {0}; 265 | char* sensor_name; 266 | 267 | sensor_name = kx13x_get_name(dev); 268 | if (sensor_name == NULL) { 269 | return KX13X_RC_ERR; 270 | } 271 | 272 | /* get accel data */ 273 | rc = kx13x_get_accel_data(dev, xyz); 274 | if (rc != KX13X_RC_OK) { 275 | return rc; 276 | } 277 | 278 | /* g to mg */ 279 | xyz_mg[0] = xyz[0] * 1000; 280 | xyz_mg[1] = xyz[1] * 1000; 281 | xyz_mg[2] = xyz[2] * 1000; 282 | 283 | if (main_cfg.adp) { 284 | /* get adp data */ 285 | rc = kx13x_get_adp_data(dev, xyz); 286 | if (rc != KX13X_RC_OK) { 287 | return rc; 288 | } 289 | /* g to mg */ 290 | adp_xyz_mg[0] = xyz[0] * 1000; 291 | adp_xyz_mg[1] = xyz[1] * 1000; 292 | adp_xyz_mg[2] = xyz[2] * 1000; 293 | } 294 | 295 | /* print data */ 296 | if (dev->plat->debug_print) { 297 | char buffer[120]; 298 | if (main_cfg.adp) { 299 | char format[] = "%s %d , %d , %d , %d , %d , %d \n"; 300 | (void)sprintf(buffer, format, "accel xyz [mg], adp xyz[mg] :", xyz_mg[0], xyz_mg[1], xyz_mg[2], adp_xyz_mg[0], adp_xyz_mg[1], adp_xyz_mg[2]); 301 | dev->plat->debug_print(dev->plat, buffer); 302 | } else { 303 | char format[] = "%s %d , %d , %d \n"; 304 | (void)sprintf(buffer, format, "accel xyz [mg] :", xyz_mg[0], xyz_mg[1], xyz_mg[2]); 305 | dev->plat->debug_print(dev->plat, buffer); 306 | } 307 | } 308 | 309 | return KX13X_RC_OK; 310 | } 311 | 312 | static int kx13x_example_report_ins_status(struct kx13x *dev) 313 | { 314 | int rc; 315 | uint8_t ins123[3]; 316 | uint8_t release_int = 0; 317 | char* sensor_name; 318 | 319 | sensor_name = kx13x_get_name(dev); 320 | if (sensor_name == NULL) { 321 | return KX13X_RC_ERR; 322 | } 323 | 324 | rc = kx13x_get_int_ins123(dev, ins123); 325 | if (rc != KX13X_RC_OK) { 326 | return rc; 327 | } 328 | 329 | #define INS1 0 330 | #define INS2 1 331 | #define INS3 2 332 | if (ins123[INS2] & KX13X_INT_INS2_DRDY) { 333 | (void)kx13x_example_read_and_print_data(dev); 334 | } 335 | 336 | if (ins123[INS3]) { 337 | char buffer[120]; 338 | 339 | //if (ins123[INS3] & KX13X_INT_INS3_WUFS) 340 | //if (ins123[INS3] & KX13X_INT_INS3_BTS) 341 | if (dev->plat->debug_print) { 342 | char format[] = "%s INS3 0x%x \n"; 343 | (void)sprintf(buffer, format, sensor_name, ins123[INS3]); 344 | dev->plat->debug_print(dev->plat, buffer); 345 | } 346 | 347 | /* release wu/bts int */ 348 | release_int = 1; 349 | } 350 | 351 | if (release_int) { 352 | (void)kx13x_release_int(dev); 353 | } 354 | 355 | return KX13X_RC_OK; 356 | } 357 | 358 | int kx13x_example_handle_interrupt(struct kx13x *dev) 359 | { 360 | int rc; 361 | uint8_t int_status; 362 | 363 | rc = kx13x_get_int_status(dev, &int_status); 364 | if (rc != KX13X_RC_OK) { 365 | return rc; 366 | } 367 | 368 | if (!(int_status & KX13X_INT_STATUS_OCCURED)) { 369 | /* no interrupt */ 370 | return KX13X_RC_OK; 371 | } 372 | 373 | rc = kx13x_example_report_ins_status(dev); 374 | if (rc != KX13X_RC_OK) { 375 | return rc; 376 | } 377 | 378 | return KX13X_RC_OK; 379 | } 380 | 381 | int kx13x_example_poll_interrupt(struct kx13x *dev) 382 | { 383 | int rc; 384 | rc = kx13x_example_report_ins_status(dev); 385 | return rc; 386 | } 387 | -------------------------------------------------------------------------------- /kx13x/kx13x_example.h: -------------------------------------------------------------------------------- 1 | /* 2 | The MIT License (MIT) 3 | Copyright (c) 2020 ROHM Co.,Ltd. 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a 6 | copy of this software and associated documentation files (the 7 | "Software"), to deal in the Software without restriction, including 8 | without limitation the rights to use, copy, modify, merge, publish, 9 | distribute, sublicense, and/or sell copies of the Software, and to 10 | permit persons to whom the Software is furnished to do so, subject to 11 | the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included 14 | in all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 17 | OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 18 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 19 | IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY 20 | CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 21 | TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 22 | SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 23 | */ 24 | 25 | #ifndef __KX13X_EXAMPLE_H__ 26 | #define __KX13X_EXAMPLE_H__ 27 | 28 | #ifdef __cplusplus 29 | extern "C" { 30 | #endif 31 | 32 | /* forward declare */ 33 | struct kx13x; 34 | struct platform; 35 | 36 | #define KX13X_EXAMPLE_DRDY_POLL 1 37 | #define KX13X_EXAMPLE_DRDY_INTERRUPT 2 38 | #define KX13X_EXAMPLE_WU_BTS_INTERRUPT 3 39 | #define KX13X_EXAMPLE_ADP_DATA 4 40 | 41 | /* writes example config to sensor, sensor is not set to operation mode */ 42 | struct kx13x_cfg *kx13x_example_update_config(struct kx13x *dev, uint8_t example); 43 | 44 | int kx13x_example_handle_interrupt(struct kx13x *dev); 45 | 46 | int kx13x_example_poll_interrupt(struct kx13x *dev); 47 | 48 | #ifdef __cplusplus 49 | } 50 | #endif 51 | 52 | #endif /* __KX13X_EXAMPLE_H__ */ 53 | 54 | -------------------------------------------------------------------------------- /kx13x/platform.h: -------------------------------------------------------------------------------- 1 | /* 2 | The MIT License (MIT) 3 | Copyright (c) 2020 ROHM Co.,Ltd. 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a 6 | copy of this software and associated documentation files (the 7 | "Software"), to deal in the Software without restriction, including 8 | without limitation the rights to use, copy, modify, merge, publish, 9 | distribute, sublicense, and/or sell copies of the Software, and to 10 | permit persons to whom the Software is furnished to do so, subject to 11 | the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included 14 | in all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 17 | OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 18 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 19 | IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY 20 | CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 21 | TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 22 | SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 23 | */ 24 | 25 | #ifndef __PLATFORM_H__ 26 | #define __PLATFORM_H__ 27 | 28 | #ifdef __cplusplus 29 | extern "C" { 30 | #endif 31 | 32 | #define PLAT_RC_OK (0) 33 | #define PLAT_RC_FAIL (-1) 34 | 35 | struct platform 36 | { 37 | void *plat_data; /* platform private data, used to identify sensor */ 38 | 39 | /* Sensor bus write function */ 40 | int (*write)(struct platform *plat, uint8_t reg, uint8_t *data, uint8_t size); 41 | 42 | /* Sensor bus read function */ 43 | int (*read)(struct platform *plat, uint8_t reg, uint8_t *data, uint8_t size); 44 | /* Delay function */ 45 | int (*delay_ms)(struct platform *plat, uint16_t ms); 46 | /* Debug print/trace function */ 47 | int (*debug_print)(struct platform *plat, char *str); 48 | }; 49 | 50 | #ifdef __cplusplus 51 | } 52 | #endif 53 | 54 | #endif /* __PLATFORM_H__ */ 55 | --------------------------------------------------------------------------------