Tiny Real-Time Clock/calendar with alarm function, battery switch-over, time stamp input, and I2C-bus
Dependencies: mbed
PCF85263AT.cpp@0:4f2e0e1e9a05, 2015-02-04 (annotated)
- Committer:
- wataaki
- Date:
- Wed Feb 04 06:13:31 2015 +0000
- Revision:
- 0:4f2e0e1e9a05
Initial version
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
wataaki | 0:4f2e0e1e9a05 | 1 | #include "mbed.h" |
wataaki | 0:4f2e0e1e9a05 | 2 | #include "PCF85263AT.h" |
wataaki | 0:4f2e0e1e9a05 | 3 | |
wataaki | 0:4f2e0e1e9a05 | 4 | I2C i2c(p28,p27); // sda, scl |
wataaki | 0:4f2e0e1e9a05 | 5 | Serial pc(USBTX, USBRX); // tx, rx |
wataaki | 0:4f2e0e1e9a05 | 6 | char cmd[32]; |
wataaki | 0:4f2e0e1e9a05 | 7 | char i; |
wataaki | 0:4f2e0e1e9a05 | 8 | dt_dat dt; // 日時構造体の変数設定 |
wataaki | 0:4f2e0e1e9a05 | 9 | |
wataaki | 0:4f2e0e1e9a05 | 10 | void set_ch(char sel) |
wataaki | 0:4f2e0e1e9a05 | 11 | { // PCA9541のサンプル |
wataaki | 0:4f2e0e1e9a05 | 12 | // MST_0側の自分にスレーブ側の制御権を得る場合 |
wataaki | 0:4f2e0e1e9a05 | 13 | cmd[0] = 1; // PCA9541 コマンドコード Cont Reg |
wataaki | 0:4f2e0e1e9a05 | 14 | i2c.write( 0xe2, cmd, 1); // Cont Regを指定 |
wataaki | 0:4f2e0e1e9a05 | 15 | i2c.read( 0xe2, cmd, 1); // Cont Regを読込み |
wataaki | 0:4f2e0e1e9a05 | 16 | wait(0.1); // 0.1s待つ |
wataaki | 0:4f2e0e1e9a05 | 17 | switch(cmd[0] & 0xf) |
wataaki | 0:4f2e0e1e9a05 | 18 | { |
wataaki | 0:4f2e0e1e9a05 | 19 | case 0: // bus off, has control |
wataaki | 0:4f2e0e1e9a05 | 20 | case 1: // bus off, no control |
wataaki | 0:4f2e0e1e9a05 | 21 | case 5: // bus on, no control |
wataaki | 0:4f2e0e1e9a05 | 22 | cmd[0] = 1; // PCA9541 コマンドコード Cont Reg |
wataaki | 0:4f2e0e1e9a05 | 23 | cmd[1] = 4; // bus on, has control |
wataaki | 0:4f2e0e1e9a05 | 24 | i2c.write( 0xe2, cmd, 2); // Cont Regにcmd[1]を書込み |
wataaki | 0:4f2e0e1e9a05 | 25 | i2c.read( 0xe2, cmd, 1); // Cont Regを読込み |
wataaki | 0:4f2e0e1e9a05 | 26 | break; |
wataaki | 0:4f2e0e1e9a05 | 27 | case 2: // bus off, no control |
wataaki | 0:4f2e0e1e9a05 | 28 | case 3: // bus off, has control |
wataaki | 0:4f2e0e1e9a05 | 29 | case 6: // bus on, no control |
wataaki | 0:4f2e0e1e9a05 | 30 | cmd[0] = 1; // PCA9541 コマンドコード Cont Reg |
wataaki | 0:4f2e0e1e9a05 | 31 | cmd[1] = 5; // bus on, has control |
wataaki | 0:4f2e0e1e9a05 | 32 | i2c.write( 0xe2, cmd, 2); // Cont Regにcmd[1]を書込み |
wataaki | 0:4f2e0e1e9a05 | 33 | i2c.read( 0xe2, cmd, 1); // Cont Regを読込み |
wataaki | 0:4f2e0e1e9a05 | 34 | break; |
wataaki | 0:4f2e0e1e9a05 | 35 | case 9: // bus on, no control |
wataaki | 0:4f2e0e1e9a05 | 36 | case 0xc: // bus on, no control |
wataaki | 0:4f2e0e1e9a05 | 37 | case 0xd: // bus off, no control |
wataaki | 0:4f2e0e1e9a05 | 38 | cmd[0] = 1; // PCA9541 コマンドコード Cont Reg |
wataaki | 0:4f2e0e1e9a05 | 39 | cmd[1] = 0; // bus on, has control |
wataaki | 0:4f2e0e1e9a05 | 40 | i2c.write( 0xe2, cmd, 2); // Cont Regにcmd[1]を書込み |
wataaki | 0:4f2e0e1e9a05 | 41 | i2c.read( 0xe2, cmd, 1); // Cont Regを読込み |
wataaki | 0:4f2e0e1e9a05 | 42 | break; |
wataaki | 0:4f2e0e1e9a05 | 43 | case 0xa: // bus on, no control |
wataaki | 0:4f2e0e1e9a05 | 44 | case 0xe: // bus off, no control |
wataaki | 0:4f2e0e1e9a05 | 45 | case 0xf: // bus on, has control |
wataaki | 0:4f2e0e1e9a05 | 46 | cmd[0] = 1; // PCA9541 コマンドコード Cont Reg |
wataaki | 0:4f2e0e1e9a05 | 47 | cmd[1] = 1; // bus on, has control |
wataaki | 0:4f2e0e1e9a05 | 48 | i2c.write( 0xe2, cmd, 2); // Cont Regにcmd[1]を書込み |
wataaki | 0:4f2e0e1e9a05 | 49 | i2c.read( 0xe2, cmd, 1); // Cont Regを読込み |
wataaki | 0:4f2e0e1e9a05 | 50 | break; |
wataaki | 0:4f2e0e1e9a05 | 51 | default: |
wataaki | 0:4f2e0e1e9a05 | 52 | break; |
wataaki | 0:4f2e0e1e9a05 | 53 | } |
wataaki | 0:4f2e0e1e9a05 | 54 | |
wataaki | 0:4f2e0e1e9a05 | 55 | cmd[0] = sel; // PCA9546 Cont Reg sel channel enabled |
wataaki | 0:4f2e0e1e9a05 | 56 | i2c.write( 0xe8, cmd, 1); // Send command string |
wataaki | 0:4f2e0e1e9a05 | 57 | } |
wataaki | 0:4f2e0e1e9a05 | 58 | |
wataaki | 0:4f2e0e1e9a05 | 59 | void get_time(dt_dat *dt) // 日時の取得 |
wataaki | 0:4f2e0e1e9a05 | 60 | { |
wataaki | 0:4f2e0e1e9a05 | 61 | cmd[0] = Seconds_100th; // 取得はレジスタSecondsから |
wataaki | 0:4f2e0e1e9a05 | 62 | i2c.write(PCF85263AT_ADDR, cmd, 1); // レジスタの設定 |
wataaki | 0:4f2e0e1e9a05 | 63 | i2c.read(PCF85263AT_ADDR, cmd, 8); // SecondsからYearsまで取得 |
wataaki | 0:4f2e0e1e9a05 | 64 | cmd[1] &= 0x7f; // 有効なのは下位7ビット |
wataaki | 0:4f2e0e1e9a05 | 65 | dt->s = (cmd[1] >> 4) * 10 + (cmd[1] & 0xf); // BCDの数値化 |
wataaki | 0:4f2e0e1e9a05 | 66 | cmd[2] &= 0x7f; // 有効なのは下位7ビット |
wataaki | 0:4f2e0e1e9a05 | 67 | dt->m = (cmd[2] >> 4) * 10 + (cmd[2] & 0xf); // BCDの数値化 |
wataaki | 0:4f2e0e1e9a05 | 68 | cmd[3] &= 0x3f; // 有効なのは下位6ビット |
wataaki | 0:4f2e0e1e9a05 | 69 | dt->h = (cmd[3] >> 4) * 10 + (cmd[3] & 0xf); // BCDの数値化 |
wataaki | 0:4f2e0e1e9a05 | 70 | cmd[4] &= 0x3f; // 有効なのは下位6ビット |
wataaki | 0:4f2e0e1e9a05 | 71 | dt->d = (cmd[4] >> 4) * 10 + (cmd[4] & 0xf); // BCDの数値化 |
wataaki | 0:4f2e0e1e9a05 | 72 | dt->wd = (cmd[5] & 0x3); // BCDの数値化 |
wataaki | 0:4f2e0e1e9a05 | 73 | cmd[6] &= 0x1f; // 有効なのは下位5ビット |
wataaki | 0:4f2e0e1e9a05 | 74 | dt->mm = (cmd[6] >> 4) * 10 + (cmd[6] & 0xf); // BCDの数値化 |
wataaki | 0:4f2e0e1e9a05 | 75 | dt->y = (cmd[7] >> 4) * 10 + (cmd[7] & 0xf); // BCDの数値化 |
wataaki | 0:4f2e0e1e9a05 | 76 | } |
wataaki | 0:4f2e0e1e9a05 | 77 | |
wataaki | 0:4f2e0e1e9a05 | 78 | void set_time(dt_dat *dt) // 日時の設定 |
wataaki | 0:4f2e0e1e9a05 | 79 | { |
wataaki | 0:4f2e0e1e9a05 | 80 | cmd[0] = Seconds_100th; // 設定はレジスタSeconds_100thから |
wataaki | 0:4f2e0e1e9a05 | 81 | cmd[1] = ((dt->s100th / 10) << 4) + (dt->s100th % 10);// 0.01秒のBCD化 |
wataaki | 0:4f2e0e1e9a05 | 82 | cmd[2] = ((dt->s / 10) << 4) + (dt->s % 10) + 0x80; // 秒のBCD化 |
wataaki | 0:4f2e0e1e9a05 | 83 | cmd[3] = ((dt->m / 10) << 4) + (dt->m % 10); // 分のBCD化 |
wataaki | 0:4f2e0e1e9a05 | 84 | cmd[4] = ((dt->h / 10) << 4) + (dt->h % 10); // 時のBCD化 |
wataaki | 0:4f2e0e1e9a05 | 85 | cmd[5] = ((dt->d / 10) << 4) + (dt->d % 10); // 日のBCD化 |
wataaki | 0:4f2e0e1e9a05 | 86 | cmd[7] = ((dt->mm / 10) << 4) + (dt->mm % 10); // 月のBCD化 |
wataaki | 0:4f2e0e1e9a05 | 87 | dt->y = dt->y - 2000; |
wataaki | 0:4f2e0e1e9a05 | 88 | cmd[8] = ((dt->y / 10) << 4) + (dt->y % 10); // 年のBCD化 |
wataaki | 0:4f2e0e1e9a05 | 89 | i2c.write(PCF85263AT_ADDR, cmd, 9); // 日時の設定 |
wataaki | 0:4f2e0e1e9a05 | 90 | } |
wataaki | 0:4f2e0e1e9a05 | 91 | |
wataaki | 0:4f2e0e1e9a05 | 92 | |
wataaki | 0:4f2e0e1e9a05 | 93 | int main () |
wataaki | 0:4f2e0e1e9a05 | 94 | { |
wataaki | 0:4f2e0e1e9a05 | 95 | i2c.frequency(100000); |
wataaki | 0:4f2e0e1e9a05 | 96 | pc.printf("PC85263AT Sample Program\r\n"); |
wataaki | 0:4f2e0e1e9a05 | 97 | |
wataaki | 0:4f2e0e1e9a05 | 98 | set_ch(1); // PC85263ATはch0に接続 |
wataaki | 0:4f2e0e1e9a05 | 99 | |
wataaki | 0:4f2e0e1e9a05 | 100 | // PC85263AT |
wataaki | 0:4f2e0e1e9a05 | 101 | /* cmd[0] = CLKOUT_ctl; // CLKOUTレジスタ設定 |
wataaki | 0:4f2e0e1e9a05 | 102 | cmd[1] = (3 << 6) + 4; // 温度測定は30s毎、出力周波数は2048Hz |
wataaki | 0:4f2e0e1e9a05 | 103 | i2c.write(PCF85263AT_ADDR, cmd, 2); // CLKOUT設定 |
wataaki | 0:4f2e0e1e9a05 | 104 | |
wataaki | 0:4f2e0e1e9a05 | 105 | cmd[0] = Aging_offset; // Aging_offsetレジスタ設定 |
wataaki | 0:4f2e0e1e9a05 | 106 | cmd[1] = 0x9; // -1ppm |
wataaki | 0:4f2e0e1e9a05 | 107 | i2c.write(PCF85263AT_ADDR, cmd, 2); // Aging_offset設定 |
wataaki | 0:4f2e0e1e9a05 | 108 | */ |
wataaki | 0:4f2e0e1e9a05 | 109 | |
wataaki | 0:4f2e0e1e9a05 | 110 | cmd[0] = Oscillator; // Aging_offsetレジスタ設定 |
wataaki | 0:4f2e0e1e9a05 | 111 | cmd[1] = 0x80 + 0x40 + 0x1; // -1ppm |
wataaki | 0:4f2e0e1e9a05 | 112 | i2c.write(PCF85263AT_ADDR, cmd, 2); // Aging_offset設定 |
wataaki | 0:4f2e0e1e9a05 | 113 | |
wataaki | 0:4f2e0e1e9a05 | 114 | cmd[0] = Function; // Aging_offsetレジスタ設定 |
wataaki | 0:4f2e0e1e9a05 | 115 | cmd[1] = 0x1; // -1ppm |
wataaki | 0:4f2e0e1e9a05 | 116 | i2c.write(PCF85263AT_ADDR, cmd, 2); // Aging_offset設定 |
wataaki | 0:4f2e0e1e9a05 | 117 | |
wataaki | 0:4f2e0e1e9a05 | 118 | cmd[0] = Offset; // Aging_offsetレジスタ設定 |
wataaki | 0:4f2e0e1e9a05 | 119 | cmd[1] = 60; // -1ppm |
wataaki | 0:4f2e0e1e9a05 | 120 | i2c.write(PCF85263AT_ADDR, cmd, 2); // Aging_offset設定 |
wataaki | 0:4f2e0e1e9a05 | 121 | |
wataaki | 0:4f2e0e1e9a05 | 122 | |
wataaki | 0:4f2e0e1e9a05 | 123 | dt.y = 2014; // 年の設定 |
wataaki | 0:4f2e0e1e9a05 | 124 | dt.mm = 10; // 月の設定 |
wataaki | 0:4f2e0e1e9a05 | 125 | dt.d = 7; // 日の設定 |
wataaki | 0:4f2e0e1e9a05 | 126 | dt.h = 10; // 時の設定 |
wataaki | 0:4f2e0e1e9a05 | 127 | dt.m = 22; // 分の設定 |
wataaki | 0:4f2e0e1e9a05 | 128 | dt.s = 0; // 秒の設定 |
wataaki | 0:4f2e0e1e9a05 | 129 | set_time(&dt); // 日時の設定 |
wataaki | 0:4f2e0e1e9a05 | 130 | |
wataaki | 0:4f2e0e1e9a05 | 131 | while(1) |
wataaki | 0:4f2e0e1e9a05 | 132 | { |
wataaki | 0:4f2e0e1e9a05 | 133 | get_time(&dt); // 日時の取得 |
wataaki | 0:4f2e0e1e9a05 | 134 | // 日時の表示 |
wataaki | 0:4f2e0e1e9a05 | 135 | pc.printf("%04d/%02d/%02d %02d:%02d:%02d\r\n", 2000 + dt.y, dt.mm, dt.d, dt.h, dt.m, dt.s); |
wataaki | 0:4f2e0e1e9a05 | 136 | wait(1); |
wataaki | 0:4f2e0e1e9a05 | 137 | } |
wataaki | 0:4f2e0e1e9a05 | 138 | } |