Mostly minor fixes up until version 0.8.10.
[irreco.git] / irtrans / irserver / src / fileio.c
blob2acbd8ce563cf2a099ded7176625230291cd5aad
1 /*
2 * Copyright (c) 2007, IRTrans GmbH
3 * All rights reserved.
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 * * Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * * Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * * Neither the name of IRTrans GmbH nor the
13 * names of its contributors may be used to endorse or promote products
14 * derived from this software without specific prior written permission.
16 * THIS SOFTWARE IS PROVIDED BY IRTrans GmbH ``AS IS'' AND ANY
17 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 * DISCLAIMED. IN NO EVENT SHALL IRTrans GmbH BE LIABLE FOR ANY
20 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
25 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30 #ifdef WIN32
31 #include <winsock2.h>
32 #include <windows.h>
33 #include <io.h>
34 #include <direct.h>
36 #define MSG_NOSIGNAL 0
37 #endif
39 #ifdef WINCE
40 #include <winsock2.h>
41 #include <windows.h>
43 #define MSG_NOSIGNAL 0
44 #endif
47 #include <stdio.h>
49 #ifdef LINUX
50 #include <stdlib.h>
51 #include <sys/types.h>
52 #include <sys/socket.h>
53 #include <netinet/in.h>
54 #include <sys/un.h>
55 #include <arpa/inet.h>
56 #include <dirent.h>
57 #include <sys/stat.h>
58 #include <errno.h>
59 #include <fcntl.h>
60 #include <signal.h>
61 #include <stdint.h>
63 typedef int SOCKET;
64 typedef int DWORD;
65 typedef int WSAEVENT;
66 #define closesocket close
67 #endif
69 #include "errcode.h"
70 #include "remote.h"
71 #include "network.h"
72 #include "dbstruct.h"
73 #include "fileio.h"
74 #include "global.h"
75 #include "lowlevel.h"
76 #include "ccf.h"
78 #define dbpath "."
80 #ifdef WIN32
81 #define PATH_SEPARATOR '\\'
82 #else
83 #define PATH_SEPARATOR '/'
84 #endif
88 #ifdef LINUX
90 int ReadIRTransDirectory (char filetype[],REMOTEBUFFER *buf,int start,byte statustype)
93 int fd,i,len,pos,res,fl,dlen;
94 long off;
95 char st[2048],msg[256];
96 struct dirent *di;
98 int cnt,cnt_total,nlen;
99 memset (buf,0,sizeof (REMOTEBUFFER));
100 buf->statustype = statustype;
101 buf->statuslen = sizeof (REMOTEBUFFER);
102 buf->offset = (short)start;
104 if (statustype == STATUS_IRDBFILE) dlen = 5;
105 else dlen = 4;
107 fd = open (".",0);
109 do {
110 len = getdirentries (fd,st,2048,&off);
112 pos = 0;
113 while (pos < len) {
114 di = (struct dirent *)&st[pos];
115 fl = strlen (di -> d_name) - dlen;
116 if (fl >= 1 && !strcmp (di->d_name + fl,filetype)) {
117 if (cnt_total >= start && cnt < 40) {
118 nlen = strlen (di -> d_name) - dlen;
119 if (nlen > 80) nlen = 80;
120 memset (buf->remotes[cnt].name,' ',80);
121 memcpy (buf->remotes[cnt].name,di -> d_name,nlen);
122 cnt++;
124 cnt_total++;
126 pos += di -> d_reclen;
128 } while (len);
130 buf->count_buffer = cnt;
131 buf->count_total = cnt_total;
132 if (cnt == 40) buf->count_remaining = cnt_total-cnt;
133 else buf->count_remaining = 0;
135 close (fd);
136 return (0);
139 #endif
142 #ifdef WIN32
144 int ReadIRTransDirectory (char filetype[],REMOTEBUFFER *buf,int start,byte statustype)
146 struct _finddata_t c_file;
147 #ifdef _M_X64
148 intptr_t hFile;
149 #else
150 int hFile;
151 #endif
153 int cnt,cnt_total,len,dlen;
154 memset (buf,0,sizeof (REMOTEBUFFER));
155 buf->statustype = statustype;
156 buf->statuslen = sizeof (REMOTEBUFFER);
157 buf->offset = (short)start;
159 if (statustype == STATUS_IRDBFILE) dlen = 5;
160 else dlen = 4;
162 cnt_total = cnt = 0;
163 if((hFile = _findfirst( filetype, &c_file )) != -1L) {
164 do {
165 if (cnt_total >= start && cnt < 40) {
166 len = (int)strlen (c_file.name) - dlen;
167 if (len > 80) len = 80;
168 memset (buf->remotes[cnt].name,' ',80);
169 memcpy (buf->remotes[cnt].name,c_file.name,len);
170 cnt++;
172 cnt_total++;
173 } while( _findnext( hFile, &c_file ) == 0);
174 _findclose( hFile );
176 buf->count_buffer = cnt;
177 buf->count_total = cnt_total;
178 if (cnt == 40) buf->count_remaining = cnt_total-cnt;
179 else buf->count_remaining = 0;
181 return (0);
184 #endif
186 void GetNumericCode (char command[],char numeric[],char rem[],char com[])
188 int b,q,z,val;
190 if (*command < '0') {
191 q = 0;
192 while (rem[q] && q < 4) {
193 sprintf (numeric + q * 2,"%02x",rem[q]);
194 q++;
196 b = 0;
197 while (com[b] && b < 4) {
198 sprintf (numeric + q * 2,"%02x",com[b]);
199 b++;
200 q++;
202 q *= 2;
203 while (q < 16) numeric[q++] = '0';
204 numeric[16] = 0;
205 return;
207 val = b = q = z = 0;
208 if (strlen (command) == 22 && !strncmp (command,"004011",6)) {
209 q = 6;
210 while (command[q]) {
211 val |= (command[q] - '0') << b;
212 b+= 2;
213 if (b == 4) {
214 val &= 0xf;
215 if (val < 10) val += '0';
216 else val += 'a' - 10;
217 numeric[z++] = val;
218 val = 0;
219 b = 0;
221 q++;
223 if (b) {
224 val &= 0xf;
225 if (val < 10) val += '0';
226 else val += 'a' - 10;
227 numeric[z++] = val;
229 while (z < 16) numeric[z++] = '0';
230 numeric[16] = 0;
231 return;
233 if (command[q] == 'S') q++;
234 while (command[q]) {
235 val |= (command[q] - '0') << b;
236 b++;
237 if (b == 4) {
238 val &= 0xf;
239 if (val < 10) val += '0';
240 else val += 'a' - 10;
241 numeric[z++] = val;
242 val = 0;
243 b = 0;
245 q++;
247 if (b) {
248 val &= 0xf;
249 if (val < 10) val += '0';
250 else val += 'a' - 10;
251 numeric[z++] = val;
253 while (z < 16) numeric[z++] = '0';
254 numeric[16] = 0;
257 FILE *ASCIIOpenRemote (char name[],NETWORKCLIENT *client)
259 FILE *fp;
260 char nm[256],st[256];
262 strcpy (nm,name);
263 if (strcmp (nm + strlen (nm) - 4,".rem")) strcat (nm,".rem");
264 fp = DBOpenFile (nm,"r");
265 memset (&client->ird,0,sizeof (IRDATA));
266 client->learnstatus.received[0] = 0;
267 client->learnstatus.adress = 0;
268 client->learnstatus.statustype = STATUS_LEARN;
269 client->learnstatus.statuslen = sizeof (NETWORKLEARNSTAT);
270 memset (client->learnstatus.remote,' ',80);
271 memset (client->learnstatus.received,' ',CODE_LEN);
272 client->learnstatus.num_timings = 0;
273 client->learnstatus.num_commands = 0;
274 client->learnstatus.learnok = 0;
276 if (fp) {
277 ASCIITimingSample (fp,client);
278 fclose (fp);
279 fp = DBOpenFile (nm,"r+");
280 memcpy (client->learnstatus.remote,name,strlen (name));
281 strcpy (client->filename,nm);
282 return (fp);
285 fp = DBOpenFile (nm,"w+");
286 if (!fp) {
287 sprintf (st,"Error opening remote file %s [%d]",nm,errno);
288 log_print (st,LOG_ERROR);
289 return (NULL);
292 fprintf (fp,"[REMOTE]\n");
293 fprintf (fp," [NAME]%s\n\n",name);
294 fprintf (fp,"[TIMING]\n");
296 fflush (fp);
298 memcpy (client->learnstatus.remote,name,strlen (name));
299 strcpy (client->filename,nm);
301 return (fp);
305 void ASCIITimingSample (FILE *fp,NETWORKCLIENT *client)
307 char ln[1000];
308 IRTIMING irt;
309 int i;
310 char *data;
311 char *rp;
314 data = DBFindSection (fp,"TIMING",NULL,NULL,NULL);
315 if (!data) return;
317 data = DBFindSection (fp,"0",ln,"[COMMANDS]",NULL);
319 if (data) {
320 StoreIRTiming (&irt,ln);
321 client->learnstatus.num_timings++;
323 while (data && *data == '[' && data[1] != 'C') {
324 data = DBReadString (ln,fp,NULL);
325 if (data && *data == '[' && data[1] != 'C') client->learnstatus.num_timings++;
328 memcpy (&client->ird.ir_length,&irt.ir_length,sizeof (IRTIMING) - 4);
329 client->ird.ir_length = 1;
332 rewind (fp);
334 data = DBFindSection (fp,"COMMANDS",NULL,NULL,NULL);
335 if (!data) return;
337 data = DBReadString (ln,fp,NULL);
338 if (!data || *data != '[') return;
340 i = (int)strlen (data);
341 while (i && data[i] != ']') i--;
342 if (!i) return;
343 i++;
345 if ((rp = strstr(data, "[RAW]")))
347 int jj;
348 rp += 5;
349 sscanf(rp, "%d", &client->ird.ir_length);
350 rp = data+i;
351 for (jj = 0;jj < client->ird.ir_length; jj++)
353 int val;
354 int len;
355 sscanf(rp, "%d%n", &val, &len);
356 client->ird.data[jj] = val/8;
357 rp += len;
360 else
362 strncpy (client->ird.data,data+i,CODE_LEN);
363 if (strlen (data+i) > CODE_LEN) client->ird.ir_length = CODE_LEN;
364 else client->ird.ir_length = (byte)strlen (data+i);
368 client->learnstatus.num_commands++;
370 while (data && *data == '[') {
371 data = DBReadString (ln,fp,NULL);
372 if (data && *data == '[') client->learnstatus.num_commands++;
377 // Sucht nach existierenden Toggle - Commands
378 int ASCIIFindToggleSeq (FILE *fp,IRDATA *ird,char name[])
381 int i,p = 0;
382 int a;
383 char ln[2048],*data;
385 rewind (fp);
386 data = DBFindSection (fp,"COMMANDS",NULL,NULL,NULL);
388 if (!data) return (-1);
389 while (data) {
390 data = DBReadString (ln,fp,NULL);
391 if (data && *data == '[') {
392 data++;
393 i = 0;
394 while (data[i] && data[i] != '#' && data[i] != ']') i++;
395 if (data[i] && !memcmp (name,data,i)) {
396 if (data[i] == ']') a = 1;
397 else a = atoi (data + i + 1) + 1;
398 while (data[i] != 'D') i++;
399 i += 2;
400 if (!strcmp (ird->data,data+i)) {
401 fseek (fp,0,SEEK_END);
402 return (-a);
404 p = a;
409 fseek (fp,0,SEEK_END);
411 return (p);
415 int ASCIIFindCommand (FILE *fp,char name[],NETWORKCLIENT *client)
418 HANDLE hfile;
419 int pos,new,len,oldlen;
420 int i;
421 char ln[2048],*data;
422 char com[256];
424 rewind (fp);
425 data = DBFindSection (fp,"COMMANDS",NULL,NULL,NULL);
427 if (!data) {
428 fseek (fp,0,SEEK_END);
429 fprintf (fp,"\n\n[COMMANDS]\n");
430 return (0);
432 strcpy (com,name);
433 ConvertLcase (com,(int)strlen (com));
434 while (data) {
435 pos = ftell (fp);
436 data = DBReadString (ln,fp,NULL);
437 if (data && *data == '[') {
438 ConvertLcase (data,(int)strlen (data));
439 data++;
440 i = 0;
441 while (data[i] && data[i] != ']') i++;
442 if (data[i] && !memcmp (com,data,i) && i == (int)strlen (com)) {
443 new = ftell (fp); // Debug Info über Update
444 oldlen = new - pos;
445 fseek (fp,0,SEEK_END);
446 len = ftell (fp) - new;
447 fseek (fp,new,SEEK_SET);
448 data = malloc (len + 1);
449 len = (int)fread (data,1,len + 1,fp);
450 fseek (fp,pos,SEEK_SET);
451 fwrite (data,1,len,fp);
452 pos = ftell (fp);
453 free (data);
454 data = malloc (oldlen);
455 memset (data,' ',oldlen);
456 fwrite (data,1,oldlen,fp);
457 fseek (fp,pos,SEEK_SET);
458 free (data);
460 if (client) {
461 #ifdef WIN32
462 hfile = CreateFile (client->filename,GENERIC_WRITE,FILE_SHARE_READ | FILE_SHARE_WRITE,NULL,OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,NULL);
463 if (hfile) {
464 SetFilePointer (hfile,pos,NULL,FILE_BEGIN);
465 SetEndOfFile (hfile);
466 CloseHandle (hfile);
468 #endif
469 #ifdef LINUX
470 truncate (client->filename,pos);
471 #endif
474 return (1);
479 fseek (fp,0,SEEK_END);
481 return (0);
486 int ASCIIStoreCommand (FILE *fp,IRDATA *ird,char name[],int timing,int seq_number)
488 int i;
490 if (seq_number) fprintf (fp," [%s#%02d][T]%d",name,seq_number,timing);
491 else fprintf (fp," [%s][T]%d",name,timing);
493 fprintf (fp,"[D]");
495 if (ird->data[0] & LONG_CODE_FLAG) {
496 for (i=0;i < ird -> ir_length-1;i++) {
497 if (i && (ird -> data[i] & 128)) { // Calibration
498 if (ird -> data[i] & 64) fprintf (fp,"#-%03d;",(ird -> data[i] & 63) * 8);
499 else fprintf (fp,"#0%03d;",(ird -> data[i] & 63) * 8);
501 else fprintf (fp,"%d%d",ird -> data[i] & 7,(ird -> data[i] >> 4) & 7);
503 fprintf (fp,"%d",ird -> data[i] & 7);
504 if (!(ird->data[0] & LONG_CODE_LEN)) fprintf (fp,"%d",(ird -> data[i] >> 4) & 7);
505 fprintf (fp,"\n");
507 else {
508 for (i=0;i < ird -> ir_length;i++) {
509 if (ird -> data[i] & 128) { // Calibration
510 if (ird -> data[i] & 64) fprintf (fp,"#-%03d;",(ird -> data[i] & 63) * 8);
511 else fprintf (fp,"#0%03d;",(ird -> data[i] & 63) * 8);
513 else fprintf (fp,"%c",ird -> data[i]);
515 fprintf (fp,"\n");
517 fflush (fp);
518 return (0);
521 int ASCIIStoreRAW (FILE *fp,IRRAW *ird,char name[])
523 int i;
524 if (ird->transmit_freq == 255)
525 fprintf (fp," [%s][RAW]%d[FREQ]455[D]",name,ird->ir_length);
526 else
527 fprintf (fp," [%s][RAW]%d[FREQ]%d[D]",name,ird->ir_length,ird->transmit_freq);
528 for (i=0;i < ird->ir_length;i++) fprintf (fp,"%d ",ird->data[i] * 8);
529 fprintf (fp,"\n");
530 fflush (fp);
531 return (0);
534 int TestTimeValue (int val,int sollk,int sollg)
536 if (val < sollk || val > sollg) return (0);
537 return (1);
541 void CheckRCMMCode (IRDATA *ird)
543 int i;
544 char msg[256];
546 if (ird->time_cnt < 3) return;
548 for (i=0;i<ird->time_cnt;i++) {
549 if (i == (ird->data[0] - '0')) {
550 if (!TestTimeValue (ird->pulse_len[i],47,60)) return;
551 if (!TestTimeValue (ird->pause_len[i],33,40)) return;
553 else {
554 if (!TestTimeValue (ird->pulse_len[i],19,26)) return;
555 if (!TestTimeValue (ird->pause_len[i],31,39) && !TestTimeValue (ird->pause_len[i],52,59) &&
556 !TestTimeValue (ird->pause_len[i],71,80) && !TestTimeValue (ird->pause_len[i],93,101)) return;
560 sprintf (msg,"RCMM Timing found\n");
561 log_print (msg,LOG_DEBUG);
563 for (i=0;i<ird->time_cnt;i++) {
564 if (TestTimeValue (ird->pulse_len[i],15,22)) ird->pulse_len[i] = 21;
565 if (TestTimeValue (ird->pulse_len[i],48,55)) ird->pulse_len[i] = 52;
566 if (TestTimeValue (ird->pause_len[i],32,40)) ird->pause_len[i] = 35;
567 if (TestTimeValue (ird->pause_len[i],53,60)) ird->pause_len[i] = 55;
568 if (TestTimeValue (ird->pause_len[i],72,80)) ird->pause_len[i] = 76;
569 if (TestTimeValue (ird->pause_len[i],93,101)) ird->pause_len[i] = 97;
571 ird->repeat_pause = 87;
572 ird->ir_repeat = 2;
573 ird->transmit_freq = 36;
578 int ASCIIStoreTiming (FILE *fp,IRDATA *ird,NETWORKLEARNSTAT *stat)
580 int pos;
581 int fpos,size;
582 char *mem;
583 char st[100];
586 CheckRCMMCode (ird);
588 pos = ASCIIFindTiming (fp,ird);
590 if (pos == -1) return (-ERR_TIMINGNOTFOUND);
592 if (pos) {
593 if (pos >= 100) {
594 fseek (fp,0,SEEK_END);
595 return (pos - 100);
597 else {
598 rewind (fp);
599 DBFindSection (fp,"TIMING",NULL,NULL,NULL);
600 sprintf (st,"%d",pos-1);
601 DBFindSection (fp,st,NULL,NULL,NULL);
602 fpos = ftell (fp);
603 fseek (fp,0,SEEK_END);
604 size = 1024 + ftell (fp) - fpos;
605 mem = malloc (size);
606 fseek (fp,fpos,SEEK_SET);
607 size = (int)fread (mem,1,size,fp);
608 fseek (fp,fpos,SEEK_SET);
609 ASCIIStoreTimingParam (fp,ird,pos);
610 fprintf (fp,"\n");
611 fwrite (mem,1,size,fp);
612 free (mem);
613 fflush (fp);
614 stat->num_timings++;
615 stat->learnok = 1;
616 return (pos);
620 fseek (fp,0,SEEK_END);
621 ASCIIStoreTimingParam (fp,ird,pos);
622 fprintf (fp,"\n\n[COMMANDS]\n");
624 stat->num_timings++;
625 stat->learnok = 1;
627 fflush (fp);
628 return (0);
632 void ASCIIStoreTimingParam (FILE *fp,IRDATA *ird,int timing)
634 int i;
636 fprintf (fp," [%d][N]%d",timing,ird->time_cnt & (TIME_LEN - 1));
637 for (i=1;i <= (ird->time_cnt & (TIME_LEN - 1));i++) {
638 fprintf (fp,"[%d]%d %d",i,ird->pulse_len[i-1] * 8,ird->pause_len[i-1] * 8);
640 fprintf (fp,"[RC]%d[RP]%d",ird->ir_repeat,ird->repeat_pause);
641 if (ird->transmit_freq == 255)
642 fprintf (fp,"[FREQ]455");
643 else
644 fprintf (fp,"[FREQ]%d",ird->transmit_freq);
645 if (ird->mode & START_BIT) fprintf (fp,"[SB]");
646 if (ird->mode & REPEAT_START) fprintf (fp,"[RS]");
647 if (ird->mode & RC5_DATA) fprintf (fp,"[RC5]");
648 if (ird->mode & RC6_DATA) fprintf (fp,"[RC6]");
652 int ASCIIFindTiming (FILE *fp,IRDATA *ird)
654 int i,flag;
655 char ln[256],*data;
656 char st[255];
657 IRTIMING irt;
660 rewind (fp);
661 data = DBFindSection (fp,"TIMING",NULL,NULL,NULL);
663 if (!data) return (-1);
665 flag = i = 0;
666 while (data) {
667 sprintf (st,"%d",i);
668 data = DBFindSection (fp,st,ln,"[COMMANDS]",NULL);
669 if (data) {
670 flag++;
671 StoreIRTiming (&irt,ln);
672 if (CompareTiming (ird,&irt)) return (i + 100);
674 i++;
678 if (!flag) fseek (fp,0,SEEK_END);
679 return (flag);
683 int CompareTiming (IRDATA *ird,IRTIMING *irt)
685 int i;
686 // Check for Timing Adjustments
688 if (ird->mode != irt->mode || ird->time_cnt != irt->time_cnt || ird->transmit_freq != ird->transmit_freq) return (0);
690 for (i=1;i < ird->ir_length;i++) if (ird->data[i] & 128) break;
692 if (i < ird->ir_length) {
693 for (i = 0;i < ird->time_cnt;i++) if (ird->pause_len[i] != irt->pause_len[i] || ird->pulse_len[i] != irt->pulse_len[i]) return (0);
696 else {
697 for (i = 0;i < ird->time_cnt;i++) {
698 if (ird->pause_len[i] < (irt->pause_len[i] - IR_TOLERANCE) || ird->pause_len[i] > (irt->pause_len[i] + IR_TOLERANCE) ||
699 ird->pulse_len[i] < (irt->pulse_len[i] - IR_TOLERANCE) || ird->pulse_len[i] > (irt->pulse_len[i] + IR_TOLERANCE)) return (0);
702 return (1);
706 IRREMOTE *rem_pnt;
707 int rem_cnt;
708 IRCOMMAND *cmd_pnt;
709 int cmd_cnt;
710 int cal_cnt;
711 IRTIMING *tim_pnt;
712 int tim_cnt;
713 MACROCOMMAND *mac_pnt;
714 int mac_cnt;
715 ROUTING *recv_routing;
716 int recv_routing_cnt;
717 ROUTING *send_routing;
718 int send_routing_cnt;
719 ROOMS *rooms;
720 int room_cnt;
721 SWITCH *switches;
722 int switch_cnt;
723 int ccf_raw;
724 int ccf_data;
725 int ccf_err;
726 APP app_pnt[30];
727 int app_cnt;
730 void GetRemoteDatabase (REMOTEBUFFER *buf,int offset)
732 int i;
733 memset (buf,0,sizeof (REMOTEBUFFER));
734 buf->statustype = STATUS_REMOTELIST;
735 buf->statuslen = sizeof (REMOTEBUFFER);
736 buf->offset = (short)offset;
738 i = 0;
739 while (i < 40 && offset < rem_cnt) {
740 memset (buf->remotes[i].name,' ',80);
741 memcpy (buf->remotes[i].name,rem_pnt[offset].name,strlen (rem_pnt[offset].name));
742 buf->remotes[i].source_mask = rem_pnt[offset].source_mask;
743 buf->remotes[i].target_mask = rem_pnt[offset].target_mask;
744 i++;
745 offset++;
748 buf->count_buffer = i;
749 buf->count_total = (word)rem_cnt;
750 if (i == 40) buf->count_remaining = (short)(rem_cnt - offset);
751 else buf->count_remaining = 0;
754 int GetCommandDatabase (COMMANDBUFFER *buf,char remote[],int offset)
756 static int nrem;
757 int i,start,tog = 0;
758 char remcmp[100];
760 memset (buf,0,sizeof (COMMANDBUFFER));
761 buf->statustype = STATUS_COMMANDLIST;
762 buf->statuslen = sizeof (COMMANDBUFFER);
763 buf->offset = (short)offset;
765 memset (remcmp,0,100);
766 strcpy (remcmp,remote);
767 ConvertLcase (remcmp,(int)strlen (remcmp));
769 if (!offset || remote[0]) {
770 nrem = DBFindRemote (remcmp);
771 if (nrem == -1) return (1);
774 start = rem_pnt[nrem].command_start;
776 i = rem_pnt[nrem].command_start;
777 while (i < rem_pnt[nrem].command_end) {
778 if (cmd_pnt[i].toggle_seq > 1) tog++;
779 i++;
783 i = 0;
784 while (i < 200 && offset < rem_pnt[nrem].command_end-start) {
785 if (cmd_pnt[offset+start].toggle_seq <= 1) {
786 memset (buf->commands[i],' ',20);
787 memcpy (buf->commands[i],cmd_pnt[offset+start].name,strlen (cmd_pnt[offset+start].name));
788 i++;
790 offset++;
793 buf->count_buffer = i;
794 buf->count_total = (word)rem_pnt[nrem].command_end - start - tog;
795 if (i == 200) buf->count_remaining = (short)(rem_pnt[nrem].command_end - start - offset - tog);
796 else buf->count_remaining = 0;
797 return (0);
800 void FreeDatabaseMemory (void)
802 if (rem_pnt) free (rem_pnt);
803 rem_pnt = 0;
804 rem_cnt = 0;
805 if (cmd_pnt) free (cmd_pnt);
806 cmd_pnt = 0;
807 cmd_cnt = 0;
808 cal_cnt = 0;
809 if (tim_pnt) free (tim_pnt);
810 tim_pnt = 0;
811 tim_cnt = 0;
812 if (mac_pnt) free (mac_pnt);
813 mac_pnt = 0;
814 mac_cnt = 0;
815 if (recv_routing) free (recv_routing);
816 recv_routing = 0;
817 recv_routing_cnt = 0;
818 if (send_routing) free (send_routing);
819 send_routing = 0;
820 send_routing_cnt = 0;
821 if (rooms) free (rooms);
822 rooms = 0;
823 room_cnt = 0;
824 ccf_data = ccf_raw = ccf_err = 0;
825 app_cnt = 0;
826 memset (app_pnt,0,sizeof (app_pnt));
829 int cmpRawData (byte *rcv,byte *mem,int len);
830 int getRawValue (byte *pnt,int pos,word *val);
832 void put_mousemovement (byte pnt[],char name[])
834 int x,y;
835 char st[10];
837 memset (st,0,sizeof (st));
839 memcpy (st,pnt+7,6);
840 y = strtoul (st,NULL,2);
841 if (y > 32) y = y - 64;
844 memcpy (st,pnt+14,6);
845 x = strtoul (st,NULL,2);
846 if (x > 32) x = x - 64;
848 sprintf (name,"%03d %03d %c%c%",x,y,pnt[20],pnt[21]);
851 int DBFindCommandName (byte command[],char remote[],char name[],byte address,int *remote_num,int *command_num,word *command_num_rel,int start)
853 int len,i;
854 byte *pnt;
855 word mask;
856 byte mode;
858 static char last_name[50];
859 static byte last_address;
860 mask = 1 << (address & 15);
861 mode = (address & 0xf0) >> 2;
862 len = (int)strlen (command);
863 i = start;
864 *command_num = *remote_num = 0;
865 if ((mode & RAW_DATA) || *command < '0') { // RAW Vergleich
866 if (mode & RAW_DATA) pnt = (byte *)command;
867 else pnt = (byte *)command + 1;
868 while (i < cmd_cnt) {
870 if (cmd_pnt[i].mode & RAW_DATA && (rem_pnt[cmd_pnt[i].remote].source_mask & mask)) {
871 if (cmpRawData (pnt,cmd_pnt[i].data,cmd_pnt[i].ir_length)) {
872 if (cmd_pnt[i].name[strlen (cmd_pnt[i].name) - 1] == '@') {
873 if (!strncmp (last_name,cmd_pnt[i].name,strlen (cmd_pnt[i].name) - 1)) {
874 strcpy (remote,rem_pnt[cmd_pnt[i].remote].name);
875 strcpy (name,cmd_pnt[i].name);
876 name[strlen (name) - 1] = 0;
877 *command_num_rel = (word)(i - rem_pnt[cmd_pnt[i].remote].command_start);
878 *command_num = i;
879 *remote_num = cmd_pnt[i].remote;
880 last_address = address;
881 return (i + 1);
884 else {
885 strcpy (remote,rem_pnt[cmd_pnt[i].remote].name);
886 strcpy (name,cmd_pnt[i].name);
887 strcpy (last_name,name);
888 *command_num_rel = (word)(i - rem_pnt[cmd_pnt[i].remote].command_start);
889 *command_num = i;
890 *remote_num = cmd_pnt[i].remote;
891 last_address = address;
892 return (i + 1);
896 i++;
898 if (!start) last_name[0] = 0;
899 return (0);
902 if (mode & RC5_DATA) command[2] = '0'; // Toggle Bit maskieren
903 if (mode & RC6_DATA) {
904 if (len == 39) command[23] = '0'; // RC6 Mode 6A
905 else command[5] = command[6] = '0'; // Toggle Bit maskieren
908 while (i < cmd_cnt) {
909 if (!cmd_pnt[i].mode && (rem_pnt[cmd_pnt[i].remote].source_mask & mask) &&
910 ((rem_pnt[cmd_pnt[i].remote].rcv_len && len >= rem_pnt[cmd_pnt[i].remote].rcv_len && !memcmp (command,cmd_pnt[i].data,rem_pnt[cmd_pnt[i].remote].rcv_len)) ||
911 (len == cmd_pnt[i].ir_length && !memcmp (command,cmd_pnt[i].data,len)))) {
912 if (cmd_pnt[i].name[strlen (cmd_pnt[i].name) - 1] == '@') {
913 if (!strncmp (last_name,cmd_pnt[i].name,strlen (cmd_pnt[i].name) - 1)) {
914 strcpy (remote,rem_pnt[cmd_pnt[i].remote].name);
915 strcpy (name,cmd_pnt[i].name);
916 name[strlen (name) - 1] = 0;
917 *command_num_rel = (word)(i - rem_pnt[cmd_pnt[i].remote].command_start);
918 *command_num = i;
919 *remote_num = cmd_pnt[i].remote;
920 last_address = address;
921 return (i + 1);
924 else {
925 strcpy (remote,rem_pnt[cmd_pnt[i].remote].name);
926 strcpy (name,cmd_pnt[i].name);
927 if (*command == 'K') strcat (name,command+9);
929 if (*command == 'M') put_mousemovement (command,name);
931 strcpy (last_name,name);
932 *command_num_rel = (word)(i - rem_pnt[cmd_pnt[i].remote].command_start);
933 *command_num = i;
934 *remote_num = cmd_pnt[i].remote;
935 last_address = address;
936 return (i + 1);
939 i++;
942 if (!start) last_name[0] = 0;
943 return (0);
947 int cmpRawData (byte *rcv,byte *mem,int len)
949 int pos = 0;
950 word recvdata,memdata;
951 getRawValue (rcv,pos,&recvdata);
952 pos = getRawValue (mem,pos,&memdata);
953 while (pos < len) {
954 if (recvdata < (memdata - (RAW_TOLERANCE + (memdata >> 4))) ||
955 recvdata > (memdata + (RAW_TOLERANCE + (memdata >> 4)))) return (0);
956 getRawValue (rcv,pos,&recvdata);
957 pos = getRawValue (mem,pos,&memdata);
959 return (1);
963 int getRawValue (byte *pnt,int pos,word *val)
965 *val = 0;
966 if (!pnt[pos]) {
967 pos++;
968 *val = pnt[pos++] << 8;
970 *val += pnt[pos++];
971 return (pos);
976 int DBFindRemoteCommand (char remote[],char command[],int *cmd_num,int *rem_num)
979 int ncmd,nrem;
981 char remcmp[100];
982 char cmdcmp[100];
984 memset (remcmp,0,100);
985 memset (cmdcmp,0,100);
987 strcpy (remcmp,remote);
988 strcpy (cmdcmp,command);
989 ConvertLcase (remcmp,(int)strlen (remcmp));
990 ConvertLcase (cmdcmp,(int)strlen (cmdcmp));
993 nrem = DBFindRemote (remcmp);
994 if (nrem == -1) return (ERR_REMOTENOTFOUND);
995 if (rem_num) *rem_num = nrem;
996 ncmd = DBFindCommand (cmdcmp,nrem);
997 if (ncmd == -1) return (ERR_COMMANDNOTFOUND);
998 *cmd_num = ncmd;
999 return (0);
1002 int DBGetRepeatCode (int cmd_num,IRDATA *ir,byte calflag)
1004 int mac_len,mac_pause;
1005 int nrem,ncmd,nrep;
1006 char cmd[100];
1008 IRMACRO *m_pnt;
1010 m_pnt = (IRMACRO *)(cmd_pnt + cmd_num);
1012 if (cmd_pnt[cmd_num].mode == MACRO_DATA) return (-1);
1014 ncmd = cmd_num;
1015 nrem = cmd_pnt[ncmd].remote;
1017 memset (cmd,' ',20);
1018 memcpy (cmd,cmd_pnt[ncmd].name,20);
1019 cmd[strlen (cmd_pnt[ncmd].name)] = '@';
1020 nrep = DBFindCommand (cmd,nrem);
1021 if (nrep == -1) return (ERR_COMMANDNOTFOUND);
1023 return (DBGetIRCode (nrep,ir,0,&mac_len,&mac_pause,0,calflag));
1026 int DBGetIRCode (int cmd_num,IRDATA *ir,int idx,int *mac_len,int *mac_pause,int *rpt_len,byte calflag)
1028 int res;
1029 int nrem,ncmd,ntim,mcmd;
1031 IRRAW *rd;
1032 IRMACRO *m_pnt;
1034 m_pnt = (IRMACRO *)(cmd_pnt + cmd_num);
1036 if (cmd_pnt[cmd_num].mode == MACRO_DATA) {
1037 *mac_len = m_pnt->macro_len;
1038 res = DBFindRemoteCommand (mac_pnt[m_pnt->macro_num + idx].mac_remote,mac_pnt[m_pnt->macro_num + idx].mac_command,&mcmd,NULL);
1039 if (res) return (res);
1040 ncmd = mcmd;
1041 *mac_pause = mac_pnt[m_pnt->macro_num + idx].pause;
1044 else {
1045 ncmd = cmd_num;
1046 *mac_len = 0;
1047 *mac_pause = 0;
1050 nrem = cmd_pnt[ncmd].remote;
1052 if (cmd_pnt[ncmd].mode & RAW_DATA) {
1053 rd = (IRRAW *)ir;
1054 memset (rd,0,sizeof (IRRAW));
1055 rd->mode = cmd_pnt[ncmd].mode;
1056 rd->target_mask = rem_pnt[nrem].target_mask;
1057 if (rem_pnt[nrem].transmitter) rd->address = rem_pnt[nrem].transmitter;
1058 if (cmd_pnt[ncmd].timing > 127) {
1059 if (cmd_pnt[ncmd].timing > 500) rd->transmit_freq = 255;
1060 else rd->transmit_freq = (byte)((cmd_pnt[ncmd].timing / 4) | 128);
1063 else rd->transmit_freq = (byte)cmd_pnt[ncmd].timing;
1064 rd->ir_length = (byte)cmd_pnt[ncmd].ir_length;
1065 memcpy (rd->data,cmd_pnt[ncmd].data,CODE_LENRAW);
1066 if (rpt_len) *rpt_len = cmd_pnt[ncmd].command_length;
1068 if (!cmd_pnt[ncmd].mode) {
1069 ntim = rem_pnt[nrem].timing_start + cmd_pnt[ncmd].timing;
1070 if (ntim >= rem_pnt[nrem].timing_end) return (ERR_TIMINGNOTFOUND);
1072 memset (ir,0,sizeof (IRDATA));
1074 ir->target_mask = rem_pnt[nrem].target_mask;
1075 if (rem_pnt[nrem].transmitter) ir->address = rem_pnt[nrem].transmitter;
1076 memcpy (&ir->transmit_freq,&tim_pnt[ntim].transmit_freq,sizeof (IRTIMING));
1078 if ((calflag && cmd_pnt[ncmd].ir_length_cal > CODE_LEN) || cmd_pnt[ncmd].ir_length > CODE_LEN) { // Long Codes packen
1079 int i,p;
1080 i = p = 0;
1081 if (calflag) {
1082 while (p < cmd_pnt[ncmd].ir_length_cal) {
1083 if (cmd_pnt[ncmd].data_cal[p] & 128) ir->data[i++] = cmd_pnt[ncmd].data_cal[p++];
1084 else {
1085 ir->data[i] = (cmd_pnt[ncmd].data_cal[p++] & 7);
1086 if (p < cmd_pnt[ncmd].ir_length_cal) ir->data[i] |= ((cmd_pnt[ncmd].data_cal[p] & 7) << 4);
1087 p++;
1088 i++;
1092 ir->data[0] |= LONG_CODE_FLAG;
1093 if (p > cmd_pnt[ncmd].ir_length_cal) ir->data[0] |= LONG_CODE_LEN;
1094 ir->ir_length = i;
1096 else {
1097 while (p < cmd_pnt[ncmd].ir_length) {
1098 if (cmd_pnt[ncmd].data[p] & 128) p++;
1099 else {
1100 ir->data[i] = (cmd_pnt[ncmd].data[p++] & 7);
1101 if (p < cmd_pnt[ncmd].ir_length) ir->data[i] |= ((cmd_pnt[ncmd].data[p] & 7) << 4);
1102 p++;
1103 i++;
1107 ir->data[0] |= LONG_CODE_FLAG;
1108 if (p > cmd_pnt[ncmd].ir_length) ir->data[0] |= LONG_CODE_LEN;
1109 ir->ir_length = i;
1112 else {
1113 if (calflag) {
1114 memcpy (ir->data,cmd_pnt[ncmd].data_cal,CODE_LEN);
1115 ir->ir_length = (byte)cmd_pnt[ncmd].ir_length_cal;
1117 else {
1118 memcpy (ir->data,cmd_pnt[ncmd].data,CODE_LEN);
1119 ir->ir_length = (byte)cmd_pnt[ncmd].ir_length;
1123 if (ir->mode & NO_TOGGLE_H) {
1124 if (ir->mode & RC5_DATA) ir->data[2] = '1';
1125 else if (ir->mode & RC6_DATA) {
1126 if (ir->ir_length == 40) ir->data[23] = '1';
1127 else ir->data[5] = '1';
1130 ir->mode &= NO_TOGGLE_H-1;
1132 if (rpt_len) {
1133 *rpt_len = cmd_pnt[ncmd].command_length;
1134 if (mac_pause && *rpt_len) *mac_pause = cmd_pnt[ncmd].pause;
1138 return (0);
1143 int DBFindRemoteCommandEx(char remote[],char command[],IRDATA *ir,byte calflag)
1146 int nrem,ncmd,ntim;
1147 IRRAW *rd;
1149 char remcmp[100];
1150 char cmdcmp[100];
1152 memset (remcmp,0,100);
1153 memset (cmdcmp,0,100);
1155 strcpy (remcmp,remote);
1156 strcpy (cmdcmp,command);
1157 ConvertLcase (remcmp,(int)strlen (remcmp));
1158 ConvertLcase (cmdcmp,(int)strlen (cmdcmp));
1161 nrem = DBFindRemote (remcmp);
1162 if (nrem == -1) return (ERR_REMOTENOTFOUND);
1163 ncmd = DBFindCommand (cmdcmp,nrem);
1164 if (ncmd == -1) return (ERR_COMMANDNOTFOUND);
1166 if (cmd_pnt[ncmd].mode == MACRO_DATA) return (ERR_ISMACRO);
1168 if (cmd_pnt[ncmd].mode & RAW_DATA) {
1169 rd = (IRRAW *)ir;
1170 memset (rd,0,sizeof (IRRAW));
1171 rd->mode = cmd_pnt[ncmd].mode;
1172 rd->target_mask = rem_pnt[nrem].target_mask;
1173 if (rem_pnt[nrem].transmitter) rd->address = rem_pnt[nrem].transmitter;
1174 // if (extended_carrier) {
1175 if (cmd_pnt[ncmd].timing > 127) {
1176 if (cmd_pnt[ncmd].timing > 500) rd->transmit_freq = 255;
1177 else rd->transmit_freq = (byte)((cmd_pnt[ncmd].timing / 4) | 128);
1179 else rd->transmit_freq = (byte)cmd_pnt[ncmd].timing;
1181 rd->ir_length = (byte)cmd_pnt[ncmd].ir_length;
1182 memcpy (rd->data,cmd_pnt[ncmd].data,CODE_LENRAW);
1184 if (!cmd_pnt[ncmd].mode) {
1185 ntim = rem_pnt[nrem].timing_start + cmd_pnt[ncmd].timing;
1186 if (ntim >= rem_pnt[nrem].timing_end) return (ERR_TIMINGNOTFOUND);
1188 memset (ir,0,sizeof (IRDATA));
1190 ir->target_mask = rem_pnt[nrem].target_mask;
1191 if (rem_pnt[nrem].transmitter) ir->address = rem_pnt[nrem].transmitter;
1192 memcpy (&ir->transmit_freq,&tim_pnt[ntim].transmit_freq,sizeof (IRTIMING));
1195 if ((calflag && cmd_pnt[ncmd].ir_length_cal > CODE_LEN) || cmd_pnt[ncmd].ir_length > CODE_LEN) { // Long Codes packen
1196 int i,p;
1197 i = p = 0;
1198 if (calflag) {
1199 while (p < cmd_pnt[ncmd].ir_length_cal) {
1200 if (cmd_pnt[ncmd].data_cal[p] & 128) ir->data[i++] = cmd_pnt[ncmd].data_cal[p++];
1201 else {
1202 ir->data[i] = (cmd_pnt[ncmd].data_cal[p++] & 7);
1203 if (p < cmd_pnt[ncmd].ir_length_cal) ir->data[i] |= ((cmd_pnt[ncmd].data_cal[p] & 7) << 4);
1204 p++;
1205 i++;
1209 ir->data[0] |= LONG_CODE_FLAG;
1210 if (p > cmd_pnt[ncmd].ir_length_cal) ir->data[0] |= LONG_CODE_LEN;
1211 ir->ir_length = i;
1213 else {
1214 while (p < cmd_pnt[ncmd].ir_length) {
1215 if (cmd_pnt[ncmd].data[p] & 128) p++;
1216 else {
1217 ir->data[i] = (cmd_pnt[ncmd].data[p++] & 7);
1218 if (p < cmd_pnt[ncmd].ir_length) ir->data[i] |= ((cmd_pnt[ncmd].data[p] & 7) << 4);
1219 p++;
1220 i++;
1224 ir->data[0] |= LONG_CODE_FLAG;
1225 if (p > cmd_pnt[ncmd].ir_length) ir->data[0] |= LONG_CODE_LEN;
1226 ir->ir_length = i;
1229 else {
1230 if (calflag) {
1231 memcpy (ir->data,cmd_pnt[ncmd].data_cal,CODE_LEN);
1232 ir->ir_length = (byte)cmd_pnt[ncmd].ir_length_cal;
1234 else {
1235 memcpy (ir->data,cmd_pnt[ncmd].data,CODE_LEN);
1236 ir->ir_length = (byte)cmd_pnt[ncmd].ir_length;
1240 if (ir->mode & NO_TOGGLE_H) {
1241 if (ir->mode & RC5_DATA) ir->data[2] = '1';
1242 else if (ir->mode & RC6_DATA) {
1243 if (ir->ir_length == 40) ir->data[23] = '1';
1244 else ir->data[5] = '1';
1247 ir->mode &= NO_TOGGLE_H-1;
1251 return (0);
1256 int DBFindCommand (char command[],int remote)
1258 int p,s;
1259 int i = rem_pnt[remote].command_start;
1260 while (i < rem_pnt[remote].command_end) {
1261 if (!memcmp (command,cmd_pnt[i].name,20)) {
1262 if (rem_pnt[remote].toggle_pos) {
1263 s = rem_pnt[remote].toggle_pos;
1264 p = i;
1265 while ((cmd_pnt[p].toggle_seq != s || memcmp (command,cmd_pnt[p].name,20)) && p < rem_pnt[remote].command_end) p++;
1266 if (cmd_pnt[p].toggle_seq == s) {
1267 rem_pnt[remote].toggle_pos++;
1268 return (p);
1270 else {
1271 rem_pnt[remote].toggle_pos = 2;
1272 return (i);
1276 else if (cmd_pnt[i].toggle_seq) {
1277 s = cmd_pnt[i].toggle_pos;
1278 p = i;
1279 while ((cmd_pnt[p].toggle_seq != s || memcmp (command,cmd_pnt[p].name,20)) && p < rem_pnt[remote].command_end) p++;
1280 if (cmd_pnt[p].toggle_seq == s) {
1281 cmd_pnt[i].toggle_pos++;
1282 return (p);
1284 else {
1285 cmd_pnt[i].toggle_pos = 2;
1286 return (i);
1289 return (i);
1291 i++;
1293 return (-1);
1297 int DBFindRemote (char remote[])
1299 int i = 0;
1300 while (i < rem_cnt) {
1301 if (!memcmp (remote,rem_pnt[i].name,80)) return (i);
1302 i++;
1304 return (-1);
1309 int StoreSwitch (word id,word num,char *rem,char *com,word mode)
1311 int i = 0;
1312 while (i < switch_cnt) {
1313 if (switches[i].id == id && switches[i].num == num) {
1314 switches[i].mode = mode;
1315 strcpy (switches[i].remote,rem);
1316 strcpy (switches[i].command,com);
1317 return (1);
1319 i++;
1322 switches = realloc (switches,(switch_cnt + 1) * sizeof (SWITCH));
1323 switches[switch_cnt].id = id;
1324 switches[switch_cnt].num = num;
1325 switches[switch_cnt].mode = mode;
1326 strcpy (switches[switch_cnt].remote,rem);
1327 strcpy (switches[switch_cnt].command,com);
1328 switch_cnt++;
1330 return (0);
1334 void WriteSwitches (void)
1336 int i = 0;
1337 char m;
1338 FILE *fp;
1340 if (switch_cnt == 0) return;
1342 fp = DBOpenFile ("switches.cfg","w");
1344 while (i < switch_cnt) {
1345 if (*switches[i].remote && *switches[i].command) {
1346 if (switches[i].mode == 1) m = 'T';
1347 if (switches[i].mode == 2) m = 'S';
1348 if (switches[i].mode == 4) m = '0';
1349 if (switches[i].mode == 8) m = '1';
1350 fprintf (fp,"[ID]%02d.%02d [NR]%d [%c] %s %s\n",switches[i].id >> 8,switches[i].id & 0xff,switches[i].num,m,switches[i].remote,switches[i].command);
1352 i++;
1355 fclose (fp);
1359 int FindSwitch (word id,word num,char *rem,char *com,word *mode)
1361 int i = 0;
1362 *mode = 0;
1363 *rem = 0;
1364 *com = 0;
1365 while (i < switch_cnt) {
1366 if (switches[i].id == id && switches[i].num == num) {
1367 *mode = switches[i].mode;
1368 strcpy (rem,switches[i].remote);
1369 strcpy (com,switches[i].command);
1370 return (1);
1372 i++;
1374 return (0);
1377 void ReadSwitches (void)
1379 FILE *fp;
1380 int i,j;
1381 char ln[2048],*data;
1382 SWITCH sw;
1384 fp = DBOpenFile ("switches.cfg","r");
1386 if (!fp) return;
1389 switch_cnt = 0;
1390 switches = 0;
1391 data = DBReadString (ln,fp,NULL);
1392 while (data) {
1393 i = 0;
1395 while (ln[i] && ln[i] != ']') i++;
1396 i++;
1397 if (ln[i+2] == '.') {
1398 ln[i+2] = 0;
1399 sw.id = atoi (ln + i) * 256 + atoi (ln + i + 3);
1400 i += 3;
1402 else sw.id = atoi (ln + i);
1404 while (ln[i] && ln[i] != ']') i++;
1405 i++;
1406 sw.num = atoi (ln + i);
1407 sw.mode = 0;
1409 while (ln[i] && ln[i] != '[') i++;
1410 i++;
1411 if (ln[i] == 'T') sw.mode = 1;
1412 if (ln[i] == 'S') sw.mode = 2;
1413 if (ln[i] == '0') sw.mode = 4;
1414 if (ln[i] == '1') sw.mode = 8;
1416 i += 2;
1418 while (ln[i] == ' ' || ln[i] == '\t') i++;
1419 j = i;
1420 while (ln[i] != ' ' && ln[i] != '\t') i++;
1421 ln[i++] = 0;
1422 strcpy (sw.remote,ln + j);
1423 while (ln[i] == ' ' || ln[i] == '\t') i++;
1424 strcpy (sw.command,ln + i);
1426 switches = realloc (switches,(switch_cnt + 1) * sizeof (SWITCH));
1427 switches[switch_cnt++] = sw;
1429 data = DBReadString (ln,fp,NULL);
1433 fclose (fp);
1436 void ReadRoutingTable (void)
1438 FILE *fp;
1440 int res;
1442 fp = DBOpenFile ("routing","r");
1444 if (!fp) return; // No routing table found
1446 res = DBStoreRooms (fp); // Read Rooms
1447 if (!res) {
1448 DBStoreRouting (fp,"SEND-ROUTING",&send_routing,&send_routing_cnt); // Read Recv Routing
1449 DBStoreRouting (fp,"RECV-ROUTING",&recv_routing,&recv_routing_cnt); // Read Send Routing
1452 fclose (fp);
1453 return;
1458 void ReadAppConfig (void)
1461 #ifdef WIN32
1462 int i,j,p,cf,res,cnum;
1463 FILE *fp;
1464 char ln[2048],*data,lchar;
1466 fp = DBOpenFile ("apps.cfg","r");
1468 if (!fp) return; // No APP Config found
1470 cf = app_cnt = 0;
1471 rewind (fp);
1473 data = ln;
1475 while (data) {
1476 data = DBReadString (ln,fp,NULL);
1477 if (!data) {
1478 fclose (fp);
1479 return;
1481 if (!strncmp (data,"[APP]",5)) {
1482 strcpy (app_pnt[app_cnt].name,data + 5);
1483 app_pnt[app_cnt].com_cnt = 0;
1485 else if (!strncmp (data,"[CLASSNAME]",11)) {
1486 strcpy (app_pnt[app_cnt].classname,data + 11);
1488 else if (!strncmp (data,"[APPNAME]",9)) {
1489 strcpy (app_pnt[app_cnt].appname,data + 9);
1491 else if (!strncmp (data,"[ACTIVE]",8)) {
1492 app_pnt[app_cnt].active = 1;
1494 else if (!strncmp (data,"[TYPE]",6)) {
1495 if (!strcmp (data+6,"MCE")) app_pnt[app_cnt].type = TYPE_MCE;
1496 if (!strcmp (data+6,"KEY")) app_pnt[app_cnt].type = TYPE_KEY;
1497 if (!strcmp (data+6,"APPCOM")) app_pnt[app_cnt].type = TYPE_APPCOM;
1498 if (!strcmp (data+6,"COM")) app_pnt[app_cnt].type = TYPE_COM;
1499 if (!strcmp (data+6,"KEYBOARD")) app_pnt[app_cnt].type = TYPE_KEYBOARD;
1500 if (!strcmp (data+6,"SCANCODE")) app_pnt[app_cnt].type = TYPE_SCANCODE;
1501 if (!strcmp (data+6,"MOUSE")) app_pnt[app_cnt].type = TYPE_MOUSE;
1502 //------------------------------------------modified------------------------------------------
1503 if (!strcmp (data+6,"SHORTCUT")) app_pnt[app_cnt].type = TYPE_SHORTCUT;
1505 else if (!strncmp (data,"[REMOTE]",8)) {
1506 strcpy (app_pnt[app_cnt].remote,data + 8);
1507 ConvertLcase (app_pnt[app_cnt].remote,(int)strlen (app_pnt[app_cnt].remote));
1508 app_pnt[app_cnt].remnum = DBFindRemote (app_pnt[app_cnt].remote);
1510 else if (!strncmp (data,"[COMMANDS]",10)) {
1511 cf = 1;
1513 else if (!strncmp (data,"[END-COMMANDS]",14)) {
1514 cf = 0;
1516 else if (!strncmp (data,"[END-APP]",9)) {
1517 app_cnt++;
1519 else if (cf) {
1520 i = 0;
1521 cnum = 0;
1522 while (data[i] && data[i] != ' ' && data[i] != '\t' && data[i] != '[') i++;
1523 if (data[i] == ' ' || data[i] == '\t') data[i++] = 0;
1524 ConvertLcase (data,(int)strlen (data));
1525 while (data[i] && data[i] != '[') i++;
1526 if (!data[i]) continue;
1527 res = DBFindRemoteCommand (app_pnt[app_cnt].remote,data,&app_pnt[app_cnt].com[app_pnt[app_cnt].com_cnt].comnum,&app_pnt[app_cnt].remnum);
1528 if (res) continue;
1529 p = i;
1530 while (data[p]) {
1531 i = p + 5;
1532 j = i;
1533 while (data[j] && data[j] != ' ' && data[j] != '\t' && data[j] != '[') j++;
1534 lchar = data[j];
1535 data[j] = 0;
1536 ConvertLcase (data+i,(int)strlen (data+i));
1537 if (!strncmp (data+p,"[FNC]",5)) {
1538 res = GetFunctionCode (app_pnt[app_cnt].type,data+i);
1539 if (!res) goto notfound;
1540 app_pnt[app_cnt].com[app_pnt[app_cnt].com_cnt].type[cnum] = app_pnt[app_cnt].type;
1541 app_pnt[app_cnt].com[app_pnt[app_cnt].com_cnt].function[cnum] = res;
1542 cnum++;
1544 else if (!strncmp (data+p,"[KEY]",5)) {
1545 res = GetKeyCode (data+i);
1546 if (!res) goto notfound;
1547 app_pnt[app_cnt].com[app_pnt[app_cnt].com_cnt].type[cnum] = TYPE_KEY;
1548 app_pnt[app_cnt].com[app_pnt[app_cnt].com_cnt].function[cnum] = res;
1549 cnum++;
1551 else if (!strncmp (data+p,"[KEF]",5)) {
1552 res = GetKeyCode (data+i);
1553 if (!res) goto notfound;
1554 app_pnt[app_cnt].com[app_pnt[app_cnt].com_cnt].type[cnum] = TYPE_KEYF;
1555 app_pnt[app_cnt].com[app_pnt[app_cnt].com_cnt].function[cnum] = res;
1556 cnum++;
1558 else if (!strncmp (data+p,"[CHR]",5)) {
1559 res = GetKeyCode (data+i);
1560 if (!res) goto notfound;
1561 app_pnt[app_cnt].com[app_pnt[app_cnt].com_cnt].type[cnum] = TYPE_CHR;
1562 app_pnt[app_cnt].com[app_pnt[app_cnt].com_cnt].function[cnum] = res;
1563 cnum++;
1565 else if (!strncmp (data+p,"[APP]",5)) {
1566 res = GetFunctionCode (TYPE_APPCOM,data+i);
1567 if (!res) goto notfound;
1568 app_pnt[app_cnt].com[app_pnt[app_cnt].com_cnt].type[cnum] = TYPE_APPCOM;
1569 app_pnt[app_cnt].com[app_pnt[app_cnt].com_cnt].function[cnum] = res;
1570 cnum++;
1572 else if (!strncmp (data+p,"[RUN]",5)) {
1573 app_pnt[app_cnt].com[app_pnt[app_cnt].com_cnt].type[cnum] = TYPE_RUN;
1574 cnum++;
1576 notfound:
1577 data[j] = lchar;
1578 p = j;
1580 if (cnum) app_pnt[app_cnt].com_cnt++;
1584 #endif
1587 void DBStoreRouting (FILE *fp,char section[],ROUTING **pnt,int *cnt)
1589 int i;
1590 char ln[2048],*data;
1592 *cnt = 0;
1593 rewind (fp);
1594 data = DBFindSection (fp,section,NULL,NULL,NULL);
1596 if (!data) return;
1598 while (data) {
1599 data = DBFindSection (fp,"REM",ln,"[END]",NULL);
1600 if (data) {
1601 i = 0;
1602 while (data[i] && data[i] != '[') i++;
1603 if (data[i] == '[') {
1604 data[i++] = 0;
1605 while (data[i] && data[i] != ']') i++;
1606 if (data[i] == ']') {
1607 i++;
1608 *pnt = realloc (*pnt,(*cnt + 1) * sizeof (ROUTING));
1609 memset (*pnt + *cnt,0,sizeof (ROUTING));
1610 if (strlen (data) > 80) data[80] = 0;
1611 ConvertLcase (data,(int)strlen (data));
1612 ((*pnt) + *cnt)->target_mask = (word)strtol (data + i,NULL,0);
1613 strncpy (((*pnt) + *cnt)->name,data,80);
1614 (*cnt)++;
1621 int DBStoreRooms (FILE *fp)
1623 int i;
1624 char ln[2048],*data;
1627 room_cnt = 0;
1628 rewind (fp);
1629 data = DBFindSection (fp,"ADDRESS",NULL,NULL,NULL);
1631 if (!data) return (-1);
1632 while (data) {
1633 data = DBFindSection (fp,"NAME",ln,NULL,NULL);
1634 if (data) {
1635 i = 0;
1636 while (data[i] && data[i] != '[') i++;
1637 if (data[i] == '[') {
1638 data[i++] = 0;
1639 while (data[i] && data[i] != ']') i++;
1640 if (data[i] == ']') {
1641 i++;
1642 rooms = realloc (rooms,(room_cnt + 1) * sizeof (ROOMS));
1643 memset (rooms + room_cnt,0,sizeof (ROOMS));
1644 if (strlen (data) > 80) data[80] = 0;
1645 ConvertLcase (data,(int)strlen (data));
1646 rooms[room_cnt].addr = atoi (data + i);
1647 strncpy (rooms[room_cnt].name,data,80);
1648 room_cnt++;
1653 return (0);
1658 int DBReadCommandFile (char remote[])
1660 FILE *fp;
1661 char includeremote[100];
1662 char st[256];
1663 int res;
1665 fp = DBOpenFile (remote,"r");
1667 if (!fp) return (ERR_DBOPENINPUT);
1669 res = DBStoreRemote (fp,includeremote);
1671 if (*includeremote) {
1672 if (strcmp (includeremote + strlen (includeremote) - 4,".rem")) strcat (includeremote,".rem");
1673 fclose (fp);
1674 fp = DBOpenFile (includeremote,"r");
1676 if (!fp) return (ERR_DBOPENINCLUDE);
1678 res = DBStoreTimings (fp);
1680 res = DBStoreCommands (fp);
1682 sprintf (st,"Remote %-20s compiled:",rem_pnt[rem_cnt].name);
1683 log_print (st,LOG_INFO);
1684 sprintf (st," %4d Timings - ",rem_pnt[rem_cnt].timing_end-rem_pnt[rem_cnt].timing_start);
1685 log_print (st,LOG_INFO);
1686 sprintf (st," %4d Commands\n",rem_pnt[rem_cnt].command_end-rem_pnt[rem_cnt].command_start);
1687 log_print (st,LOG_INFO);
1689 rem_cnt++;
1691 fclose (fp);
1692 return (0);
1696 void FindDuplicateCommands (void)
1698 int i = 0,j;
1699 int cnt;
1700 char st[255];
1702 while (i < cmd_cnt) {
1703 j = i + 1;
1704 if (cmd_pnt[i].mode == 0 && cmd_pnt[i].name[strlen (cmd_pnt[i].name) - 1] != '@') {
1705 cnt = 0;
1706 while (j < cmd_cnt) {
1707 if (cmd_pnt[j].mode == 0 && cmd_pnt[j].name[strlen (cmd_pnt[j].name) - 1] != '@') {
1708 if (cmd_pnt[i].ir_length == cmd_pnt[j].ir_length && !memcmp (cmd_pnt[j].data,cmd_pnt[i].data,cmd_pnt[i].ir_length)) {
1709 if (!cnt) {
1710 sprintf (st,"Duplicate Commands for %s.%s: ",rem_pnt[cmd_pnt[i].remote].name,cmd_pnt[i].name);
1711 log_print (st,LOG_ERROR);
1713 sprintf (st," %s.%s",rem_pnt[cmd_pnt[j].remote].name,cmd_pnt[j].name);
1714 log_print (st,LOG_ERROR);
1715 cnt++;
1718 j++;
1720 if (cnt) {
1721 sprintf (st,"\n");
1722 log_print (st,LOG_ERROR);
1725 i++;
1730 void DBShowStatus (void)
1732 char st[256];
1733 sprintf (st,"Total: %3d Remotes - %3d Timings - %4d Commands - %4d Calib. Commands\n",rem_cnt,tim_cnt,cmd_cnt,cal_cnt);
1734 FindDuplicateCommands ();
1735 log_print (st,LOG_INFO);
1736 sprintf (st," %3d CCF Data - %3d CCF RAW - %4d CCF Error\n",ccf_data,ccf_raw,ccf_err);
1737 log_print (st,LOG_INFO);
1740 int DBStoreCommands (FILE *fp)
1742 int i,p,j,ccf_rpt,ccf_pause,cmd_length,n,res,maxlen,ntim;
1743 char ln[2048],*data,st[255];
1744 IRMACRO *m_pnt;
1746 rem_pnt[rem_cnt].command_start = cmd_cnt;
1747 rem_pnt[rem_cnt].command_end = cmd_cnt;
1748 rewind (fp);
1749 if (time_len == TIME_LEN) maxlen = CODE_LENRAW;
1750 else maxlen = OLD_LENRAW;
1751 data = DBFindSection (fp,"COMMANDS",NULL,NULL,NULL);
1753 if (!data) return (-1);
1754 while (data) {
1755 data = DBReadString (ln,fp,NULL);
1756 if (data && *data == '[') {
1757 ccf_rpt = ccf_pause = cmd_length = 0;
1758 data++;
1759 i = 0;
1760 while (data[i] && data[i] != ']') i++;
1761 if (data[i]) {
1762 cmd_pnt = realloc (cmd_pnt,(cmd_cnt + 1) * sizeof (IRCOMMAND));
1763 memset (cmd_pnt + cmd_cnt,0,sizeof (IRCOMMAND));
1764 data[i++] = 0;
1765 if (strlen (data) > 20) data[20] = 0;
1766 ConvertLcase (data,(int)strlen (data));
1767 if (data[strlen (data) - 3] == '#') {
1768 data[strlen (data) - 3] = 0;
1769 memcpy (cmd_pnt[cmd_cnt].name,data,strlen (data));
1770 j = cmd_cnt - 1;
1771 if (atoi (data + strlen (data) + 1) == 1) while (j >= 0) {
1772 if (!memcmp (cmd_pnt[j].name,cmd_pnt[cmd_cnt].name,20) && !cmd_pnt[j].toggle_seq) {
1773 cmd_pnt[j].toggle_seq = 1;
1774 cmd_pnt[j].toggle_pos = 1;
1775 j = 0;
1777 j--;
1779 cmd_pnt[cmd_cnt].toggle_seq = atoi (data + strlen (data) + 1) + 1;
1781 else {
1782 cmd_pnt[cmd_cnt].toggle_seq = 0;
1783 memcpy (cmd_pnt[cmd_cnt].name,data,strlen (data));
1786 cmd_pnt[cmd_cnt].toggle_pos = 0;
1787 cmd_pnt[cmd_cnt].remote = rem_cnt;
1788 if (!memcmp (data + i,"[RL]",4)) {
1789 i += 4;
1790 cmd_length = atoi (data + i);
1791 while (data[i] && data[i] != '[') i++;
1793 if (!memcmp (data + i,"[RC]",4)) {
1794 i += 4;
1795 ccf_rpt = atoi (data + i);
1796 ccf_pause = 0;
1797 while (data[i] && data[i] != '[') i++;
1799 if (!memcmp (data + i,"[RP]",4)) {
1800 i += 4;
1801 ccf_pause = atoi (data + i);
1802 while (data[i] && data[i] != '[') i++;
1804 if (!memcmp (data + i,"[RAW]",5)) {
1805 cmd_pnt[cmd_cnt].command_length = cmd_length;
1806 cmd_pnt[cmd_cnt].mode = RAW_DATA;
1807 i += 5;
1808 p = i;
1809 while (data[i] && data[i] != '[') i++;
1810 data[i++] = 0;
1811 cmd_pnt[cmd_cnt].ir_length = atoi (data+p);
1812 if (cmd_pnt[cmd_cnt].ir_length <= maxlen) {
1813 i += 5;
1814 p = i;
1815 while (data[i] && data[i] != '[') i++;
1816 data[i++] = 0;
1817 cmd_pnt[cmd_cnt].timing = atoi (data+p);
1818 i += 2;
1819 p = i;
1820 i = 0;
1821 while (i < cmd_pnt[cmd_cnt].ir_length) {
1822 cmd_pnt[cmd_cnt].data[i] = atoi (data + p) / 8;
1823 while (data[p] && data[p] != ' ') p++;
1824 p++;
1825 i++;
1827 cmd_cnt++;
1830 else if (!memcmp (data + i,"[MACRO]",7)) {
1831 m_pnt = (IRMACRO *)&cmd_pnt[cmd_cnt];
1832 cmd_pnt[cmd_cnt].mode = MACRO_DATA;
1834 i += 7;
1835 p = i;
1836 while (data[i] && data[i] != '[') i++;
1837 data[i++] = 0;
1838 m_pnt->macro_len = atoi (data+p);
1839 m_pnt->macro_num = mac_cnt;
1841 mac_pnt = realloc (mac_pnt,(mac_cnt + m_pnt->macro_len) * sizeof (MACROCOMMAND));
1842 memset (mac_pnt[mac_cnt].mac_remote,0,m_pnt->macro_len * sizeof (MACROCOMMAND));
1843 for (n=0;n < m_pnt->macro_len && !strncmp (data+i,"IR]",3);n++) {
1844 i += 3;
1845 if (data[i++] != '[') break;
1846 p = i;
1847 while (data[i] && data[i] != ']') i++;
1848 if (data[i] != ']') break;
1849 data[i++] = 0;
1850 strcpy (mac_pnt[mac_cnt + n].mac_remote,data + p);
1851 if (data[i++] != '[') break;
1852 p = i;
1853 while (data[i] && data[i] != ']') i++;
1854 if (data[i] != ']') break;
1855 data[i++] = 0;
1856 strcpy (mac_pnt[mac_cnt + n].mac_command,data + p);
1857 if (data[i++] != '[') break;
1858 p = i;
1859 while (data[i] && data[i] != ']') i++;
1860 if (data[i] != ']') break;
1861 data[i++] = 0;
1862 mac_pnt[mac_cnt + n].pause = atoi (data + p);
1863 i++;
1866 m_pnt->macro_len = n;
1867 mac_cnt += n;
1868 cmd_cnt++;
1871 else if (!memcmp (data + i,"[CCF]",5)) {
1872 cmd_pnt[cmd_cnt].command_length = cmd_length;
1873 res = DBStoreCCFCode (data + i + 5);
1874 if (!res) {
1875 sprintf (st,"**** CCF Error: %s [See below for Remote name]\n",cmd_pnt[cmd_cnt].name);
1876 log_print (st,LOG_ERROR);
1878 else cmd_cnt += res;
1880 else {
1881 cmd_pnt[cmd_cnt].pause = ccf_pause;
1882 cmd_pnt[cmd_cnt].command_length = cmd_length;
1883 cmd_pnt[cmd_cnt].timing = atoi (data + i + FindLineSection (data+i,"T"));
1884 ntim = rem_pnt[rem_cnt].timing_start + cmd_pnt[cmd_cnt].timing;
1886 if (ntim < rem_pnt[rem_cnt].timing_end) {
1887 tim_pnt[ntim].link_count++;
1888 strcpy (cmd_pnt[cmd_cnt].data,data + i + FindLineSection (data+i,"D"));
1889 ReadCalibrateData (cmd_pnt[cmd_cnt].data,cmd_pnt[cmd_cnt].data_cal);
1890 if (tim_pnt[rem_pnt[cmd_pnt[cmd_cnt].remote].timing_start + cmd_pnt[cmd_cnt].timing].mode == IRDA_DATA) ConvertIRDARAW (cmd_pnt[cmd_cnt].data);
1891 cmd_pnt[cmd_cnt].ir_length = (word)strlen (cmd_pnt[cmd_cnt].data);
1892 cmd_pnt[cmd_cnt].ir_length_cal = (word)strlen (cmd_pnt[cmd_cnt].data_cal);
1893 cmd_pnt[cmd_cnt].mode = 0;
1894 if (tim_pnt[cmd_pnt[cmd_cnt].timing + rem_pnt[rem_cnt].timing_start].time_cnt <= time_len) cmd_cnt++;
1903 rem_pnt[rem_cnt].command_end = cmd_cnt;
1904 return (0);
1908 void ReadCalibrateData (byte *pnt,byte *pntcal)
1910 int j = 0,i = 0,val;
1912 while (pnt[i]) {
1913 if (pnt[i] == '#') break;
1914 i++;
1916 if (!pnt[i]) {
1917 strcpy (pntcal,pnt);
1918 return;
1921 cal_cnt++;
1922 i = 0;
1923 while (pnt[i]) {
1924 if (pnt[i] == '#') {
1925 i++;
1926 pnt[i+4] = 0;
1927 val = atoi(pnt+i) / 8;
1928 pntcal[j] = (byte)(abs (val)) | 128;
1929 if (val < 0) pntcal[j] |= 64;
1930 j++;
1931 i += 5;
1933 else pntcal[j++] = pnt[i++];
1935 pntcal[j] = 0;
1937 i = j = 0;
1938 while (pntcal[i]) {
1939 if (pntcal[i] & 128) i++;
1940 else pnt[j++] = pntcal[i++];
1942 pnt[j] = 0;
1945 void ConvertIRDARAW (char data[])
1947 int i,j;
1948 char tar[255];
1950 i = j = 0;
1953 tar[j++] = '0';
1955 for (i=0;data[i] && j < CODE_LEN;i++) {
1956 tar[j++] = data[i];
1958 if (!((i+1) % 8)) {
1959 tar[j++] = '1';
1960 if (data[i+1]) tar[j++] = '0';
1964 tar[j] = 0;
1965 strcpy (data,tar);
1968 int DBStoreCCFCode (char cd[])
1970 int res;
1971 IRDATA ird;
1972 IRRAW *irr;
1974 res = DecodeCCF (cd,&ird,START);
1976 if (res <= 0) {
1977 ccf_err++;
1978 return (0);
1981 if (res & 4) {
1982 ccf_raw++;
1983 irr = (IRRAW *)&ird;
1985 cmd_pnt[cmd_cnt].mode = irr->mode;
1987 cmd_pnt[cmd_cnt].ir_length = irr->ir_length;
1988 cmd_pnt[cmd_cnt].timing = irr->transmit_freq;
1990 memcpy (cmd_pnt[cmd_cnt].data,irr->data,irr->ir_length);
1992 if (res & 1) {
1993 cmd_cnt++;
1995 cmd_pnt = realloc (cmd_pnt,(cmd_cnt + 1) * sizeof (IRCOMMAND));
1996 memset (cmd_pnt + cmd_cnt,0,sizeof (IRCOMMAND));
1997 cmd_pnt[cmd_cnt].toggle_seq = 0;
1998 memcpy (cmd_pnt[cmd_cnt].name,cmd_pnt[cmd_cnt-1].name,strlen (cmd_pnt[cmd_cnt-1].name));
1999 strcat (cmd_pnt[cmd_cnt].name,"@");
2001 DecodeCCF (cd,&ird,REPEAT);
2002 cmd_pnt[cmd_cnt].mode = irr->mode;
2004 cmd_pnt[cmd_cnt].ir_length = irr->ir_length;
2005 cmd_pnt[cmd_cnt].timing = irr->transmit_freq;
2007 memcpy (cmd_pnt[cmd_cnt].data,irr->data,irr->ir_length);
2008 cmd_pnt[cmd_cnt].remote = rem_cnt;
2011 return (1);
2014 if (res & 2) {
2015 ccf_data++;
2017 tim_pnt = realloc (tim_pnt,(tim_cnt + 1) * sizeof (IRTIMING));
2018 memset (&tim_pnt[tim_cnt],0,sizeof (IRTIMING));
2020 memcpy (&tim_pnt[tim_cnt].ir_length,&ird.ir_length,sizeof (IRTIMING) - 4);
2022 cmd_pnt[cmd_cnt].mode = 0;
2024 cmd_pnt[cmd_cnt].ir_length = ird.ir_length;
2025 cmd_pnt[cmd_cnt].timing = tim_cnt - rem_pnt[rem_cnt].timing_start;
2026 cmd_pnt[cmd_cnt].remote = rem_cnt;
2028 memcpy (cmd_pnt[cmd_cnt].data,ird.data,ird.ir_length);
2030 memcpy (cmd_pnt[cmd_cnt].data_cal,ird.data,ird.ir_length); // Später ggf. auch Calibrate für CCF
2031 cmd_pnt[cmd_cnt].ir_length_cal = ird.ir_length;
2033 tim_cnt++;
2034 if (res & 1) {
2035 cmd_cnt++;
2037 cmd_pnt = realloc (cmd_pnt,(cmd_cnt + 1) * sizeof (IRCOMMAND));
2038 memset (cmd_pnt + cmd_cnt,0,sizeof (IRCOMMAND));
2039 cmd_pnt[cmd_cnt].toggle_seq = 0;
2040 memcpy (cmd_pnt[cmd_cnt].name,cmd_pnt[cmd_cnt-1].name,strlen (cmd_pnt[cmd_cnt-1].name));
2041 strcat (cmd_pnt[cmd_cnt].name,"@");
2043 DecodeCCF (cd,&ird,REPEAT);
2044 tim_pnt = realloc (tim_pnt,(tim_cnt + 1) * sizeof (IRTIMING));
2045 memset (&tim_pnt[tim_cnt],0,sizeof (IRTIMING));
2047 memcpy (&tim_pnt[tim_cnt].ir_length,&ird.ir_length,sizeof (IRTIMING) - 4);
2049 cmd_pnt[cmd_cnt].mode = 0;
2051 cmd_pnt[cmd_cnt].ir_length = ird.ir_length;
2052 cmd_pnt[cmd_cnt].timing = tim_cnt - rem_pnt[rem_cnt].timing_start;
2053 cmd_pnt[cmd_cnt].remote = rem_cnt;
2055 memcpy (cmd_pnt[cmd_cnt].data,ird.data,ird.ir_length);
2057 memcpy (cmd_pnt[cmd_cnt].data_cal,ird.data,ird.ir_length); // Später ggf. auch Calibrate für CCF
2058 cmd_pnt[cmd_cnt].ir_length_cal = ird.ir_length;
2060 tim_cnt++;
2064 rem_pnt[rem_cnt].timing_end = tim_cnt;
2065 return (1);
2068 return (0);
2072 int DBStoreTimings (FILE *fp)
2074 int i;
2075 char st[100];
2076 char ln[256],*data;
2079 rem_pnt[rem_cnt].timing_start = tim_cnt;
2080 rem_pnt[rem_cnt].timing_end = tim_cnt;
2082 rewind (fp);
2083 data = DBFindSection (fp,"TIMING",NULL,NULL,NULL);
2085 if (!data) return (-1);
2087 i = 0;
2088 while (data) {
2089 sprintf (st,"%d",i);
2090 data = DBFindSection (fp,st,ln,"[COMMANDS]",NULL);
2091 if (data) {
2092 tim_pnt = realloc (tim_pnt,(tim_cnt + 1) * sizeof (IRTIMING));
2093 StoreIRTiming (tim_pnt + tim_cnt,ln);
2094 tim_cnt++;
2096 i++;
2098 rem_pnt[rem_cnt].timing_end = tim_cnt;
2100 return (0);
2104 int DBStoreRemote (FILE *fp,char newremote[])
2106 char name[100],*data,tra[100];
2108 newremote[0] = 0;
2110 rem_pnt = realloc (rem_pnt,(rem_cnt + 1) * sizeof (IRREMOTE));
2112 data = DBFindSection (fp,"REMOTE",NULL,NULL,NULL);
2114 if (!data) return (-1);
2116 data = DBFindSection (fp,"NAME",name,"[TIMING]",NULL);
2118 if (!data) return (-1);
2121 memset (&rem_pnt[rem_cnt],0,sizeof (IRREMOTE));
2122 ConvertLcase (data,(int)strlen (data));
2123 strncpy (rem_pnt[rem_cnt].name,data,80);
2124 rem_pnt[rem_cnt].number = rem_cnt;
2125 GetRemoteAddressMask (rem_cnt);
2127 data = DBFindSection (fp,"GLOBAL-TOGGLE",NULL,NULL,NULL);
2128 if (data) rem_pnt[rem_cnt].toggle_pos = 1;
2130 rewind (fp);
2132 data = DBFindSection (fp,"TRANSMITTER",tra,"[TIMING]",NULL);
2133 if (data) {
2134 ConvertLcase (data,(int)strlen (data));
2135 if (!strcmp (data,"extern") || !strcmp (data,"external")) rem_pnt[rem_cnt].transmitter = EXTERNAL_LEDS;
2136 if (!strcmp (data,"intern") || !strcmp (data,"internal")) rem_pnt[rem_cnt].transmitter = INTERNAL_LEDS;
2137 if (!strcmp (data,"both") || !strcmp (data,"beide") || !strcmp (data,"all") || !strcmp (data,"alle")) rem_pnt[rem_cnt].transmitter = INTERNAL_LEDS | EXTERNAL_LEDS;
2140 rewind (fp);
2142 data = DBFindSection (fp,"RCV-LEN",tra,"[TIMING]",NULL);
2143 if (data) rem_pnt[rem_cnt].rcv_len = (byte)atoi (data);
2144 else rem_pnt[rem_cnt].rcv_len = 0;
2146 rewind (fp);
2148 data = DBFindSection (fp,"INCLUDE",newremote,NULL,NULL);
2150 return (0);
2153 void GetRemoteAddressMask (int num)
2155 int i = 0;
2157 rem_pnt[num].target_mask = 0xffff;
2158 rem_pnt[num].source_mask = 0xffff;
2160 while (i < send_routing_cnt) {
2161 if (!memcmp (rem_pnt[num].name,send_routing[i].name,80)) {
2162 rem_pnt[num].target_mask = send_routing[i].target_mask;
2164 i++;
2167 i = 0;
2168 while (i < recv_routing_cnt) {
2169 if (!memcmp (rem_pnt[num].name,recv_routing[i].name,80)) {
2170 rem_pnt[num].source_mask = recv_routing[i].target_mask;
2172 i++;
2176 void StoreIRTiming (IRTIMING *irp,char data[])
2178 int i = 0,p,flag = 0,rp;
2179 char cm[10],par[100];
2181 memset (irp,0,sizeof (IRTIMING));
2182 irp -> transmit_freq = 39;
2184 while (data[i]) {
2185 if (data[i] == '[') {
2186 i++;
2187 p = 0;
2188 while (data[i] && data[i] != ']') cm[p++] = data[i++];
2189 cm[p] = 0;
2190 p = i+1;
2191 while (data[i] && data[i] != '[') i++;
2192 strncpy (par,data+p,i-p);
2193 par[i-p] = 0;
2194 if (!strcmp (cm,"N")) irp -> time_cnt |= atoi (par);
2195 if (*cm >= '1' && *cm <= TIME_LEN + 48) StorePulseTiming (irp,cm,par);
2196 if (!strcmp (cm,"RC")) irp -> ir_repeat = atoi (par);
2197 if (!strcmp (cm,"RP")) irp -> repeat_pause = (rp = atoi (par));
2198 if (!strcmp (cm,"SB")) irp -> mode |= START_BIT;
2199 if (!strcmp (cm,"RS")) irp -> mode |= REPEAT_START;
2200 if (!strcmp (cm,"NOTOG")) flag = 1;
2201 if (!strcmp (cm,"NOTOG1")) flag = 2;
2202 if (!strcmp (cm,"FREQ")) {
2203 if (atoi (par) > 127) {
2204 if (atoi (par) > 500) irp -> transmit_freq = 255;
2205 else irp -> transmit_freq = (atoi (par) / 4) | 128;
2207 else irp -> transmit_freq = atoi (par);
2209 if (!strcmp (cm,"RC5")) irp -> mode |= RC5_DATA;
2210 if (!strcmp (cm,"RC6")) irp -> mode |= RC6_DATA;
2211 if (!strcmp (cm,"IRDA-RAW")) {
2212 irp -> mode = IRDA_DATA | START_BIT;
2213 irp -> transmit_freq = 0;
2214 irp -> repeat_pause = rp / 100;
2216 if (!strcmp (cm,"IRDA")) {
2217 irp -> mode = IRDA_DATA;
2218 irp -> transmit_freq = 0;
2219 irp -> repeat_pause = rp / 100;
2222 else i++;
2224 if (!((irp ->mode & IRDA_DATA) == IRDA_DATA) && irp -> mode & (RC5_DATA | RC6_DATA)) {
2225 irp -> mode &= ~START_MASK;
2226 if (flag) irp -> mode |= NO_TOGGLE;
2227 if (flag == 2) irp -> mode |= NO_TOGGLE_H;
2231 void StorePulseTiming (IRTIMING *irp,char cmd[],char data[])
2233 int i = 0;
2235 while (data[i] && data[i] >= '0') i++;
2237 if (!data[i]) return;
2238 data[i++] = 0;
2240 irp ->pulse_len[atoi (cmd)-1] = atoi (data) / 8;
2241 irp ->pause_len[atoi (cmd)-1] = atoi (data+i) / 8;
2244 int FindLineSection (char ln[],char section[])
2246 unsigned int pnt,len;
2247 char cmp[256];
2249 sprintf (cmp,"[%s]",section);
2251 len = (int)strlen (cmp);
2253 pnt = 0;
2255 while (len + pnt < strlen (ln)) {
2256 if (!memcmp (ln+pnt,cmp,len)) return (pnt+len);
2257 pnt++;
2260 return (-1);
2265 FILE *DBOpenFile (char remote[],char mode[])
2267 char nm[255];
2269 sprintf (nm,"%s%c%s",dbpath,PATH_SEPARATOR,remote);
2271 return (fopen (nm,mode));
2275 char *DBFindSection (FILE *fp,char section[],char data[],char end[],int *fpos)
2277 int len;
2278 static char ln[2048];
2279 char *pnt;
2280 char cmp[256];
2282 sprintf (cmp,"[%s]",section);
2283 len = (int)strlen (cmp);
2285 pnt = DBReadString (ln,fp,fpos);
2286 while (pnt) {
2287 if (end && !strcmp (ln,end)) return (0);
2288 if (!strncmp (pnt,cmp,len)) {
2289 if (data) strcpy (data,pnt+len);
2290 return (pnt+len);
2292 pnt = DBReadString (ln,fp,fpos);
2294 return (0);
2298 char *DBReadString (char ln[],FILE *fp,int *fpos)
2300 int i;
2301 char *pnt;
2303 do {
2304 if (fpos) *fpos = ftell (fp);
2305 pnt = fgets (ln,2048,fp);
2306 if (!pnt) return (NULL);
2307 while (*pnt == ' ' || *pnt == '\t') pnt++;
2309 i = (int)strlen (pnt) - 1;
2311 while (i && pnt[i-1] && ((byte)pnt[i-1]) <= ' ') i--;
2313 if (((byte)pnt[i]) <= ' ') pnt[i] = 0;
2314 } while (*pnt == 0);
2316 return (pnt);
2319 void ConvertLcase (char *pnt,int len)
2321 int i = 0;
2322 while (i < len) {
2323 pnt[i] = tolower (pnt[i]);
2324 i++;