パリティ入りの独自規格赤外線通信ライブラリ。受送信がセットになっています
Dependents: ROBOX_Sample_IRcon
ROBOXformat.cpp@0:966615bf0d02, 2016-10-08 (annotated)
- Committer:
- natuga117
- Date:
- Sat Oct 08 23:21:10 2016 +0000
- Revision:
- 0:966615bf0d02
publish
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
natuga117 | 0:966615bf0d02 | 1 | #include "ROBOXformat.h" |
natuga117 | 0:966615bf0d02 | 2 | ROBOXformat::ROBOXformat(PinName irin, double delay) |
natuga117 | 0:966615bf0d02 | 3 | { |
natuga117 | 0:966615bf0d02 | 4 | button = new InterruptIn(irin); |
natuga117 | 0:966615bf0d02 | 5 | signal_ignore_flag=false; |
natuga117 | 0:966615bf0d02 | 6 | //button->mode(PullDown); |
natuga117 | 0:966615bf0d02 | 7 | IRinit(delay); |
natuga117 | 0:966615bf0d02 | 8 | } |
natuga117 | 0:966615bf0d02 | 9 | ROBOXformat::~ROBOXformat() |
natuga117 | 0:966615bf0d02 | 10 | { |
natuga117 | 0:966615bf0d02 | 11 | delete button; |
natuga117 | 0:966615bf0d02 | 12 | } |
natuga117 | 0:966615bf0d02 | 13 | void ROBOXformat::IR_timeout(void) |
natuga117 | 0:966615bf0d02 | 14 | { |
natuga117 | 0:966615bf0d02 | 15 | if (signal_change_flag == true) { data = 0;} |
natuga117 | 0:966615bf0d02 | 16 | signal_timeout_flag=false; |
natuga117 | 0:966615bf0d02 | 17 | } |
natuga117 | 0:966615bf0d02 | 18 | void ROBOXformat::IR_ON(void) { |
natuga117 | 0:966615bf0d02 | 19 | |
natuga117 | 0:966615bf0d02 | 20 | //if(signal_progress!=0) |
natuga117 | 0:966615bf0d02 | 21 | if(signal_ignore_flag)return; |
natuga117 | 0:966615bf0d02 | 22 | s_timer[1]+=t.read_us(); |
natuga117 | 0:966615bf0d02 | 23 | t.reset(); |
natuga117 | 0:966615bf0d02 | 24 | int bit=code_check(); |
natuga117 | 0:966615bf0d02 | 25 | switch(bit) |
natuga117 | 0:966615bf0d02 | 26 | { |
natuga117 | 0:966615bf0d02 | 27 | case -1://ノイズ。不正データの場合 |
natuga117 | 0:966615bf0d02 | 28 | break; |
natuga117 | 0:966615bf0d02 | 29 | case 2://リーダーコードの場合 |
natuga117 | 0:966615bf0d02 | 30 | signal_progress=0; |
natuga117 | 0:966615bf0d02 | 31 | break; |
natuga117 | 0:966615bf0d02 | 32 | case 0: |
natuga117 | 0:966615bf0d02 | 33 | case 1://データの場合 |
natuga117 | 0:966615bf0d02 | 34 | recieve_bit[signal_progress]=bit; |
natuga117 | 0:966615bf0d02 | 35 | signal_progress++; |
natuga117 | 0:966615bf0d02 | 36 | if(signal_progress>=LAST_PROGRESS) |
natuga117 | 0:966615bf0d02 | 37 | { |
natuga117 | 0:966615bf0d02 | 38 | signal_progress=0; |
natuga117 | 0:966615bf0d02 | 39 | dataset(); |
natuga117 | 0:966615bf0d02 | 40 | } |
natuga117 | 0:966615bf0d02 | 41 | break; |
natuga117 | 0:966615bf0d02 | 42 | } |
natuga117 | 0:966615bf0d02 | 43 | |
natuga117 | 0:966615bf0d02 | 44 | } |
natuga117 | 0:966615bf0d02 | 45 | int ROBOXformat::code_check(void) |
natuga117 | 0:966615bf0d02 | 46 | { |
natuga117 | 0:966615bf0d02 | 47 | if((s_timer[0]>SIGNAL_T*15)&&(s_timer[0]<=SIGNAL_T*17)&&(s_timer[1]>SIGNAL_T*6)&&(s_timer[1]<=SIGNAL_T*9)) |
natuga117 | 0:966615bf0d02 | 48 | {s_timer[0]=0;s_timer[1]=0;return 2;//リーダーコードの場合 |
natuga117 | 0:966615bf0d02 | 49 | }else if((s_timer[0]>SIGNAL_T*0.5)&&(s_timer[0]<=SIGNAL_T*1.5)) |
natuga117 | 0:966615bf0d02 | 50 | { |
natuga117 | 0:966615bf0d02 | 51 | if((s_timer[1]>SIGNAL_T*2.0)&&(s_timer[1]<=SIGNAL_T*3.5)) |
natuga117 | 0:966615bf0d02 | 52 | { |
natuga117 | 0:966615bf0d02 | 53 | s_timer[0]=0;s_timer[1]=0;return 0; |
natuga117 | 0:966615bf0d02 | 54 | }else if((s_timer[1]>SIGNAL_T*0.5)&&(s_timer[1]<=SIGNAL_T*2.0)) |
natuga117 | 0:966615bf0d02 | 55 | { |
natuga117 | 0:966615bf0d02 | 56 | s_timer[0]=0;s_timer[1]=0;return 1; |
natuga117 | 0:966615bf0d02 | 57 | } |
natuga117 | 0:966615bf0d02 | 58 | }else if((s_timer[1]>SIGNAL_T*9)||(s_timer[0]>SIGNAL_T*17)) |
natuga117 | 0:966615bf0d02 | 59 | { |
natuga117 | 0:966615bf0d02 | 60 | s_timer[0]=0;s_timer[1]=0;return -1; |
natuga117 | 0:966615bf0d02 | 61 | }else if(s_timer[1]>s_timer[0]) |
natuga117 | 0:966615bf0d02 | 62 | { |
natuga117 | 0:966615bf0d02 | 63 | s_timer[1]+=s_timer[0];s_timer[0]=0;return 3; |
natuga117 | 0:966615bf0d02 | 64 | }else |
natuga117 | 0:966615bf0d02 | 65 | { |
natuga117 | 0:966615bf0d02 | 66 | s_timer[0]+=s_timer[1];s_timer[0]=0;return 3; |
natuga117 | 0:966615bf0d02 | 67 | } |
natuga117 | 0:966615bf0d02 | 68 | |
natuga117 | 0:966615bf0d02 | 69 | s_timer[0]=0;s_timer[1]=0;return -1;//拾われなかった=不正な信号 |
natuga117 | 0:966615bf0d02 | 70 | } |
natuga117 | 0:966615bf0d02 | 71 | void ROBOXformat::IR_OFF(void) { |
natuga117 | 0:966615bf0d02 | 72 | if(signal_ignore_flag)return; |
natuga117 | 0:966615bf0d02 | 73 | s_timer[0]+=t.read_us(); |
natuga117 | 0:966615bf0d02 | 74 | t.reset(); |
natuga117 | 0:966615bf0d02 | 75 | } |
natuga117 | 0:966615bf0d02 | 76 | |
natuga117 | 0:966615bf0d02 | 77 | void ROBOXformat::IRinit(double delay) |
natuga117 | 0:966615bf0d02 | 78 | { |
natuga117 | 0:966615bf0d02 | 79 | signal_change_flag=false; |
natuga117 | 0:966615bf0d02 | 80 | signal_timeout_flag=false; |
natuga117 | 0:966615bf0d02 | 81 | grobal_signal = false; |
natuga117 | 0:966615bf0d02 | 82 | no_signal_delay=delay; |
natuga117 | 0:966615bf0d02 | 83 | t.start(); |
natuga117 | 0:966615bf0d02 | 84 | button->rise(this, &ROBOXformat::IR_OFF); |
natuga117 | 0:966615bf0d02 | 85 | button->fall(this, &ROBOXformat::IR_ON); |
natuga117 | 0:966615bf0d02 | 86 | } |
natuga117 | 0:966615bf0d02 | 87 | unsigned char ROBOXformat::encode_ECC(unsigned char data) |
natuga117 | 0:966615bf0d02 | 88 | { |
natuga117 | 0:966615bf0d02 | 89 | unsigned char b[8],i; |
natuga117 | 0:966615bf0d02 | 90 | for (i = 0; i < 8; i++) { |
natuga117 | 0:966615bf0d02 | 91 | b[i] = data & 1; |
natuga117 | 0:966615bf0d02 | 92 | data >>= 1; |
natuga117 | 0:966615bf0d02 | 93 | } |
natuga117 | 0:966615bf0d02 | 94 | /*戻り値にパリティを格納*/ |
natuga117 | 0:966615bf0d02 | 95 | return |
natuga117 | 0:966615bf0d02 | 96 | (b[0] ^ b[2] ^ b[4] ^ b[6]) << 5 //p[0] |
natuga117 | 0:966615bf0d02 | 97 | | (b[1] ^ b[3] ^ b[5] ^ b[7]) << 4 //q[0] |
natuga117 | 0:966615bf0d02 | 98 | | (b[0] ^ b[1] ^ b[4] ^ b[5]) << 3 //p[1] |
natuga117 | 0:966615bf0d02 | 99 | | (b[2] ^ b[3] ^ b[6] ^ b[7]) << 2 //q[1] |
natuga117 | 0:966615bf0d02 | 100 | | (b[0] ^ b[1] ^ b[2] ^ b[3]) << 1 //p[2] |
natuga117 | 0:966615bf0d02 | 101 | | (b[4] ^ b[5] ^ b[6] ^ b[7]); //q[2] |
natuga117 | 0:966615bf0d02 | 102 | /*ECCのアルゴリズムは(http://community.osdev.info/index.php?ECC)にある |
natuga117 | 0:966615bf0d02 | 103 | サンプル+α(8ビット目に1を指定)を参考にして作りました |
natuga117 | 0:966615bf0d02 | 104 | */ |
natuga117 | 0:966615bf0d02 | 105 | } |
natuga117 | 0:966615bf0d02 | 106 | unsigned char ROBOXformat::decode_ECC(unsigned char data,unsigned char ecc) |
natuga117 | 0:966615bf0d02 | 107 | { |
natuga117 | 0:966615bf0d02 | 108 | unsigned char pardata=0,comparison=0,i=0; |
natuga117 | 0:966615bf0d02 | 109 | pardata = encode_ECC(data);//受信データをもとにパリティを作成 |
natuga117 | 0:966615bf0d02 | 110 | if(pardata!=ecc)//実際に作ったパリティと比較 |
natuga117 | 0:966615bf0d02 | 111 | { |
natuga117 | 0:966615bf0d02 | 112 | /*受信データ内に誤りあり*/ |
natuga117 | 0:966615bf0d02 | 113 | comparison=pardata; |
natuga117 | 0:966615bf0d02 | 114 | comparison^=ecc; |
natuga117 | 0:966615bf0d02 | 115 | if(comparison == (1<<1|1<<3|1<<5))data ^= 1; |
natuga117 | 0:966615bf0d02 | 116 | else if(comparison == (1<<1|1<<3|1<<4))data ^= (1<<1); |
natuga117 | 0:966615bf0d02 | 117 | else if(comparison == (1<<1|1<<2|1<<5))data ^= (1<<2); |
natuga117 | 0:966615bf0d02 | 118 | else if(comparison == (1<<1|1<<2|1<<4))data ^= (1<<3); |
natuga117 | 0:966615bf0d02 | 119 | else if(comparison == (1 |1<<3|1<<5))data ^= (1<<4); |
natuga117 | 0:966615bf0d02 | 120 | else if(comparison == (1 |1<<3|1<<4))data ^= (1<<5); |
natuga117 | 0:966615bf0d02 | 121 | else if(comparison == (1 |1<<2|1<<5))data ^= (1<<6); |
natuga117 | 0:966615bf0d02 | 122 | else if(comparison == (1 |1<<3|1<<4))data ^= (1<<7);//ビット列の誤りを修正 |
natuga117 | 0:966615bf0d02 | 123 | else |
natuga117 | 0:966615bf0d02 | 124 | { |
natuga117 | 0:966615bf0d02 | 125 | //ここまで来たらECCのエラーまたは2bit以上の誤り(修復不可能)の場合である |
natuga117 | 0:966615bf0d02 | 126 | ecc=0;for(i=0;i<6;i++){if(comparison & 1 << i )ecc++;}//食い違うビットの数を確認(とりあえずeccに格納) |
natuga117 | 0:966615bf0d02 | 127 | if(ecc==1)return data;//ECCのエラーと判定(ビット修正無し) |
natuga117 | 0:966615bf0d02 | 128 | return 0;//そうじゃない場合=2bit以上の誤りにより修復不可能なノイズを検知(戻り値0b10000000) |
natuga117 | 0:966615bf0d02 | 129 | } |
natuga117 | 0:966615bf0d02 | 130 | } |
natuga117 | 0:966615bf0d02 | 131 | return data; |
natuga117 | 0:966615bf0d02 | 132 | } |
natuga117 | 0:966615bf0d02 | 133 | void ROBOXformat::dataset(void) |
natuga117 | 0:966615bf0d02 | 134 | { |
natuga117 | 0:966615bf0d02 | 135 | int bdata=0,eccs=0; |
natuga117 | 0:966615bf0d02 | 136 | for(int i=1;i<5;i++){if(recieve_bit[i]!=recieve_bit[9-i])return;}//反転データに誤りが無いかの確認 |
natuga117 | 0:966615bf0d02 | 137 | if(!(recieve_bit[0]))for(int i=1;i<5;i++){if(recieve_bit[i]!=Ccode[i-1])return;}//カスタムコードと一致しているかの確認 |
natuga117 | 0:966615bf0d02 | 138 | for(int i=0;i<8;i++){ |
natuga117 | 0:966615bf0d02 | 139 | bdata|=(recieve_bit[10+i]<<i); |
natuga117 | 0:966615bf0d02 | 140 | if(i<6)eccs|=(recieve_bit[18+i]<<i); |
natuga117 | 0:966615bf0d02 | 141 | } |
natuga117 | 0:966615bf0d02 | 142 | if(recieve_bit[0]==1) |
natuga117 | 0:966615bf0d02 | 143 | { |
natuga117 | 0:966615bf0d02 | 144 | gl_data=decode_ECC(bdata,eccs); |
natuga117 | 0:966615bf0d02 | 145 | for(int i=1;i<5;i++){gl_address[i-1]=recieve_bit[i];} |
natuga117 | 0:966615bf0d02 | 146 | }else |
natuga117 | 0:966615bf0d02 | 147 | { |
natuga117 | 0:966615bf0d02 | 148 | data=decode_ECC(bdata,eccs); |
natuga117 | 0:966615bf0d02 | 149 | IrTimeout.attach(this, &ROBOXformat::IR_timeout,no_signal_delay); |
natuga117 | 0:966615bf0d02 | 150 | signal_change_flag=true; |
natuga117 | 0:966615bf0d02 | 151 | grobal_signal = false; |
natuga117 | 0:966615bf0d02 | 152 | } |
natuga117 | 0:966615bf0d02 | 153 | } |
natuga117 | 0:966615bf0d02 | 154 | void ROBOXformat::send_code(PinName s,unsigned int data,bool global) |
natuga117 | 0:966615bf0d02 | 155 | { |
natuga117 | 0:966615bf0d02 | 156 | int sdata[25],ecc; |
natuga117 | 0:966615bf0d02 | 157 | PwmOut signal(s); |
natuga117 | 0:966615bf0d02 | 158 | signal.period(1.0/38000);//38khz変調を掛けるため、周期を変更 |
natuga117 | 0:966615bf0d02 | 159 | signal=0;//消す |
natuga117 | 0:966615bf0d02 | 160 | signal_ignore_flag=true; |
natuga117 | 0:966615bf0d02 | 161 | ecc=encode_ECC(data); |
natuga117 | 0:966615bf0d02 | 162 | if(global){sdata[0]=1;sdata[9]=0;}else{sdata[0]=0;sdata[9]=0;}//服従bit設定 |
natuga117 | 0:966615bf0d02 | 163 | for (int i = 0; i < 4; i++) { |
natuga117 | 0:966615bf0d02 | 164 | sdata[1+i] = Ccode[i]; |
natuga117 | 0:966615bf0d02 | 165 | sdata[8-i] = Ccode[i]; |
natuga117 | 0:966615bf0d02 | 166 | } |
natuga117 | 0:966615bf0d02 | 167 | for (int i = 0; i < 8; i++) { |
natuga117 | 0:966615bf0d02 | 168 | sdata[10+i] = data & 1; |
natuga117 | 0:966615bf0d02 | 169 | data >>= 1; |
natuga117 | 0:966615bf0d02 | 170 | } |
natuga117 | 0:966615bf0d02 | 171 | for (int i = 0; i < 6; i++) { |
natuga117 | 0:966615bf0d02 | 172 | sdata[18+i] = ecc & 1; |
natuga117 | 0:966615bf0d02 | 173 | ecc >>= 1; |
natuga117 | 0:966615bf0d02 | 174 | } |
natuga117 | 0:966615bf0d02 | 175 | sdata[24] = 1;//終端ビット指定 |
natuga117 | 0:966615bf0d02 | 176 | //リーダーコード送信 |
natuga117 | 0:966615bf0d02 | 177 | signal=0.33;//付ける |
natuga117 | 0:966615bf0d02 | 178 | wait_us(SIGNAL_T*16); |
natuga117 | 0:966615bf0d02 | 179 | signal=0;//消す |
natuga117 | 0:966615bf0d02 | 180 | wait_us(SIGNAL_T*8); |
natuga117 | 0:966615bf0d02 | 181 | |
natuga117 | 0:966615bf0d02 | 182 | for(int i=0;i<25;i++) |
natuga117 | 0:966615bf0d02 | 183 | { |
natuga117 | 0:966615bf0d02 | 184 | signal=0.33;//付ける |
natuga117 | 0:966615bf0d02 | 185 | wait_us(SIGNAL_T); |
natuga117 | 0:966615bf0d02 | 186 | signal=0;//消す |
natuga117 | 0:966615bf0d02 | 187 | if(sdata[i]==0){//ここの待機時間によって0,1が変化 |
natuga117 | 0:966615bf0d02 | 188 | wait_us(SIGNAL_T*3); |
natuga117 | 0:966615bf0d02 | 189 | }else{ |
natuga117 | 0:966615bf0d02 | 190 | wait_us(SIGNAL_T); |
natuga117 | 0:966615bf0d02 | 191 | } |
natuga117 | 0:966615bf0d02 | 192 | } |
natuga117 | 0:966615bf0d02 | 193 | //DigitalIn aa(s); |
natuga117 | 0:966615bf0d02 | 194 | //delete &signal; |
natuga117 | 0:966615bf0d02 | 195 | signal_ignore_flag=false; |
natuga117 | 0:966615bf0d02 | 196 | } |
natuga117 | 0:966615bf0d02 | 197 | unsigned int ROBOXformat::getData() |
natuga117 | 0:966615bf0d02 | 198 | { |
natuga117 | 0:966615bf0d02 | 199 | return data; |
natuga117 | 0:966615bf0d02 | 200 | } |
natuga117 | 0:966615bf0d02 | 201 | unsigned int ROBOXformat::get_glData() |
natuga117 | 0:966615bf0d02 | 202 | { |
natuga117 | 0:966615bf0d02 | 203 | return gl_data; |
natuga117 | 0:966615bf0d02 | 204 | } |
natuga117 | 0:966615bf0d02 | 205 | unsigned int ROBOXformat::takeData() |
natuga117 | 0:966615bf0d02 | 206 | { |
natuga117 | 0:966615bf0d02 | 207 | unsigned int buf; |
natuga117 | 0:966615bf0d02 | 208 | buf=data;data=0; |
natuga117 | 0:966615bf0d02 | 209 | return buf; |
natuga117 | 0:966615bf0d02 | 210 | } |
natuga117 | 0:966615bf0d02 | 211 | unsigned int ROBOXformat::take_glData() |
natuga117 | 0:966615bf0d02 | 212 | { |
natuga117 | 0:966615bf0d02 | 213 | unsigned int buf; |
natuga117 | 0:966615bf0d02 | 214 | buf=gl_data;gl_data=0; |
natuga117 | 0:966615bf0d02 | 215 | return buf; |
natuga117 | 0:966615bf0d02 | 216 | }unsigned int ROBOXformat::take_glData_With_address(int code[4]) |
natuga117 | 0:966615bf0d02 | 217 | { |
natuga117 | 0:966615bf0d02 | 218 | unsigned int buf; |
natuga117 | 0:966615bf0d02 | 219 | buf=gl_data;gl_data=0; |
natuga117 | 0:966615bf0d02 | 220 | for(int i=0;i<4;i++){code[i]=gl_address[i];} |
natuga117 | 0:966615bf0d02 | 221 | return buf; |
natuga117 | 0:966615bf0d02 | 222 | } |
natuga117 | 0:966615bf0d02 | 223 | void ROBOXformat::printData() |
natuga117 | 0:966615bf0d02 | 224 | { |
natuga117 | 0:966615bf0d02 | 225 | int bitbuf=data; |
natuga117 | 0:966615bf0d02 | 226 | printf("Ccode:"); |
natuga117 | 0:966615bf0d02 | 227 | for(int i=0;i<10;i++){printf("%d",recieve_bit[i]);} |
natuga117 | 0:966615bf0d02 | 228 | printf(" data:"); |
natuga117 | 0:966615bf0d02 | 229 | for(int i=0;i<8;i++){printf("%d",bitbuf&1);bitbuf>>=1;} |
natuga117 | 0:966615bf0d02 | 230 | } |
natuga117 | 0:966615bf0d02 | 231 | void ROBOXformat::printglData() |
natuga117 | 0:966615bf0d02 | 232 | { |
natuga117 | 0:966615bf0d02 | 233 | int bitbuf=gl_data; |
natuga117 | 0:966615bf0d02 | 234 | printf(" gldata:"); |
natuga117 | 0:966615bf0d02 | 235 | for(int i=0;i<8;i++){printf("%d",bitbuf&1);bitbuf>>=1;} |
natuga117 | 0:966615bf0d02 | 236 | } |