File: main.cc

package info (click to toggle)
sms-pl 1.9.2m-3
  • links: PTS
  • area: main
  • in suites: etch, etch-m68k
  • size: 620 kB
  • ctags: 355
  • sloc: cpp: 2,143; ansic: 1,046; perl: 272; makefile: 113; sh: 97
file content (681 lines) | stat: -rw-r--r-- 22,137 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
#include <limits.h>
#include <pwd.h>
#include <sys/types.h>
#include <sys/param.h>
#include <sys/stat.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <signal.h>
#include <unistd.h>
#include <ctype.h>
#include <iostream>
#include <strstream>
#include <string>
#include "vsprintf.h"
#include "headers.h"
#include "request.h"
#include "sms.h"

#ifdef ADDR_BOOK
#include "addrbook.h"
#endif

const char *info_msg = 
"\tsms, wersja: %s, skompilowano %s %s\n"\
"Wysylanie wiadomosci na telefony sieci Era, Plus GSM i Idea Centertel.\n\n"\
"Uzycie:\n\tsms [ opcje ] <nr_telefonu> [ wiadomosc ... ]\n\n"\
"Opcje:\n"\
"--split n  : dluzsze wiadomosci zostana podzielone na maksymalnie n SMS'ow\n"\
"             (domyslnie %d)\n"\
"--czat     : sms jest wysylany przez bramke Idea.czat; do pliku .smsrc\n"\
"             nalezy wtedy wpisac swoj login oraz haslo w usludze Idea.czat\n"\
"--dlogin   : login, na ktory ma byc wyslany sms w usludze Idea.czat\n"\
"--1rstwap  : sms jest wysylany przez bramke www.1rstwap.com; do pliku .smsrc\n"\
"             nalezy wtedy wpisac swoj login oraz haslo w serwisie\n"\
"--plusmail : sms do PLusGSM jest wysylany mailem a nie przez bramke www\n"\
"--mplusa   : sms jest wysylany bramka www.miastoplusa.pl, nalezy oczywiscie\n"\
"             wpisac swoj login i haslo do pliku .smsrc\n"\
"--eranet   : sms do Ery jest wysylany bramka Eranet (jako mail)\n"\
"--mbox     : sms jest wysylany bramka z portalu www.idea.pl\n"\
"--nike     : uzywana jest bramka nikewoman.com (Idea, Era)\n"\
"--cfg plik : nazwa pliku konfiguracyjnego do wykorzystania\n"\
"--check    : sprawdza czy na stronie programu jest dostepna nowa wersja\n"\
"--from     : ustawia adres mailowy nadawcy (dla PlusGSM oraz Idea)\n"\
"--ip       : ustawia adres IP z ktorego beda wysylane SMSy\n"\
"--quiet    : nie drukuje na konsoli zadnych komunikatow\n"\
"--no-error : zawsze zwraca kod wyjscia 0\n"\
"--sign     : ustawia podpis SMSa (domyslnie pusty)\n"\
"--thanksto : wyswietla liste osob, ktore poswiecily swoj czas i wiedze na rozwoj programu\n"\
"nr telefonu: podany bez kodu kraju, czyli np. 602123456 lub 501123456\n"\
"wiadomosc  : tekst do wyslania, jesli nie podano wiadomosci w linii polecen\n"\
"             to zostanie ona odczytana ze standardowego wejscia.\n\n"\
"Smsy do Ery wysylane sa bezplatna bramka EraOmnix - trzeba miec tam konto.\n"\
"Uzywasz tego programu \"takim jakim jest\", nie ponosze zadnej odpowiedzialnosci\n"\
"za skutki wynikle z jego uzycia badz niemoznosci uzycia. Komentarze, uwagi,\n"\
"informacje o bledach prosze przesylac poczta na moj adres.\n\n"\
"Aktualna wersje programu zawsze bedzie mozna pobrac ze strony pod adresem\n"\
"http://ceti.pl/~miki/komputery/sms.html\n"\
"Adres listy uzytkownikow programu: sms-users@ma.krakow.pl\n\n"\
"Mikolaj Rydzewski <miki@ceti.pl>\n\n";

int WyslijSMS_Era(SMS_packet *);
//int WyslijSMS_Idea(SMS_packet *);
int WyslijSMS_Plus(SMS_packet *);
//int WyslijSMS_ICQ(SMS_packet *);
int WyslijSMS_Idea_czat(SMS_packet *);
int WyslijSMS_Eranet(SMS_packet *);
int WyslijSMS_Wap_com(SMS_packet *);
int WyslijSMS_Nike(SMS_packet *sms);
int WyslijSMS_MiastoPlusa(SMS_packet *sms);
int WyslijSMS_IDEA_mBox(SMS_packet *sms);
#ifdef DEBUG
int WyslijSMS_Test(SMS_packet *);
#endif

#ifdef FOR_QMAIL 
#define SMS_FATAL 100
#define SMS_SOFTERR  111
#else
#define SMS_FATAL 2
#define SMS_SOFTERR 1
#endif

#define SMS_OK 0
#define SMS_TIMEOUT 3

#define ERA_GSM 0
#define PLUS_GSM 1
#define IDEA_GSM 2
#define FREE 3
#define ICQ  4
#define SUPERSMS  5
#define CZAT 6
#define BRAMKAORG 7
#define PF 8
#define SMSC 9
#define ERANET 10
#define WAP 11
#define NIKE 12
#define MPLUSA 13
#define IDEAMBOX 14
#define TEST 15


// struktura zawiera wskaznik do funkcji wysylajacej sms'a, maksymalna
// dlugosc SMS przekazywana przez bramke oraz tekst, ktory jest zwracany
// przez serwer operatora w przypadku pomyslnego wyslania SMSa
static struct { sms_func gsm; int max_len; char *ok_msg; } GSM_Oper[] = 
	{ {WyslijSMS_Era, 125, "X-ERA-counter"},
	  {WyslijSMS_Plus, 1200, "Twoja wiadomo zostaa wysana na numer <B><I>48%s"},
	  {(sms_func)(NULL), 140, "Your message is sent !"/*"Krtka wiadomo tekstowa zostaa wysana do odbiorcy"*/},
	  {(sms_func)(NULL)/*WyslijSMS_FreeSMS*/, 436, ""},
	  {(sms_func)(NULL)/*WyslijSMS_ICQ*/, 160, ""},
	  {(sms_func)(NULL)/*WyslijSMS_SuperSMS*/, 480, "OK"},
	  {WyslijSMS_Idea_czat, 135, ""},
	  {(sms_func)(NULL)/*WyslijSMS_Bramka_org*/, 160, "SMS zosta poprawnie wysany"},
	  {(sms_func)(NULL)/*WyslijSMS_PF*/, 466, "Wiadomo. SMS zostaa wysana na numer %s"},
	  {(sms_func)(NULL)/*WyslijSMS_Smsc_pl*/, 160, ""}
	, {WyslijSMS_Eranet, 160, ""}
	, {WyslijSMS_Wap_com, 160, ""}
	, {WyslijSMS_Nike, 160, ""}
	, {WyslijSMS_MiastoPlusa, 320, ""}
	, {WyslijSMS_IDEA_mBox, 640, ".*"}
#ifdef DEBUG
	, {WyslijSMS_Test, 80, "Przyjeto wiadomosc:"}
#endif
	};
	
Debug *debug_stream;

TKonfig konfig;

// struktura uzywana podczas parsowania linii polecen
typedef struct {
	int nsplit;	// ilosc kawalkow na ktory dzielimy sms
	int otherOper;	// id bramki, jesli wysylamy przez jakies specjalne
	char telefon[10]; // numer na ktory wysylamy smsa
	char sms[2048];	// tresc sms'a, 
	char cfg[MAXPATHLEN]; // opcjonalna sciezka do pliku konfiguracyjnego
	int check_ver,  // ustawione jesli program ma sprawdzic czy jest nowa
	                // wersja
	    thanksto;	// ustawione jesli mamy pokazac liste contributorow
        char podpis[11]; // podpis
} Targs;

int ktora_siec(const char *nr);
void odczytaj_konfig(const char *cfg=NULL);
void odczytaj_w3cache(char *);
int wyslij_sms(Targs &args);
int sprawdz_nowa_wersje();
void thanksto();

// hmmm - skoro juz tutaj doszlismy, to znaczy ze wybil alarm, czyli
// program podejrzanie dlugo wysylal cos przez bramke, pewnie cos padlo
// po drodze
void sig_alarm(int sig)
{
	debug_stream->Log(LOG_INFO,"Proces ubity sygnalem SIGALRM");
	if (!konfig.quiet) cerr << "Proces zostal ubity sygnalem SIGALRM" << endl;
	exit(konfig.no_error ? 0 : SMS_TIMEOUT);
}

// przeanalizuje parametry podane w linii polecen. wszystkie potrzebne dane
// wpisze do struktury args. zwroci 1, jesli bedzie trzeba pokazac strone
// z tekstem pomocy
int sprawdz_argumenty(char **argv, int argc, Targs &args)
{
	int tick = 1, start_arg = 1;
	
	while (start_arg < argc) {
		tick = 0;
		if (!strcmp(argv[start_arg], "--split")) {
			// jesli jest to ostatni argument to wywalamy blad,
			// dalej musi sie jeszcze zmiescic parametr
			if ((start_arg+1) >= argc) return 1;
			args.nsplit = atoi(argv[start_arg+1]);
			start_arg++;
			tick = 1;
		}

		if (!strcmp(argv[start_arg], "--cfg")) {
			// jesli jest to ostatni argument to wywalamy blad,
			// dalej musi sie jeszcze zmiescic parametr
			if ((start_arg+1) >= argc) return 1;
			strncpy(args.cfg, argv[start_arg+1], sizeof(args.cfg)-1);
			start_arg++;
			tick = 1;
		}

		if (!strcmp(argv[start_arg], "--mplusa")) {
			args.otherOper = MPLUSA;
			tick = 1;
		}
		if (!strcmp(argv[start_arg], "--eranet")) {
			args.otherOper = ERANET;
			tick = 1;
		}
		if (!strcmp(argv[start_arg], "--nike")) {
			args.otherOper = NIKE;
			tick = 1;
		}

		if (!strcmp(argv[start_arg], "--ip")) {
			if ((start_arg+1) >= argc) return 1;
			tick = 1;
			strncpy(konfig.srcip, argv[start_arg+1], sizeof(konfig.srcip)-1);
			start_arg++;
		}

		if (!strcmp(argv[start_arg], "--quiet")) {
			konfig.quiet = 1;
			tick = 1;
		}
		if (!strcmp(argv[start_arg], "--no-error")) {
			konfig.no_error = 1;
			tick = 1;
		}

		if (!strcmp(argv[start_arg], "--plusmail")) {
			tick = 1;
			konfig.plus_mail = 1;
		}

		if (!strcmp(argv[start_arg], "--from")) {
			if ((start_arg+1) >= argc) return 1;
			tick = 1;
			strncpy(konfig.mailaddr, argv[start_arg+1], sizeof(konfig.mailaddr)-1);
			start_arg++;
		}

		if (!strcmp(argv[start_arg], "--sign")) {
			if ((start_arg+1) >= argc) return 1;
			tick = 1;
			strncpy(konfig.sign, argv[start_arg+1], sizeof(konfig.sign)-1);
			start_arg++;
		}

		if (!strcmp(argv[start_arg], "--check")) {
			tick = 1;
			args.check_ver = 1;
			// nieladnie tak wychodzic w srodku, no ale nic ;-)
			return 0;
		}

		if (!strcmp(argv[start_arg], "--thanksto")) {
			tick = 1;
			args.thanksto = 1;
			// nieladnie tak wychodzic w srodku, no ale nic ;-)
			return 0;
		}

		if (!strcmp(argv[start_arg], "--czat")) {
			args.otherOper = CZAT;
			tick = 1;
		}

		if (!strcmp(argv[start_arg], "--dlogin")) {
			if ((start_arg+1) >= argc) return 1;
			strncpy(konfig.dlogin, argv[start_arg+1], sizeof(konfig.dlogin)-1);
			start_arg++;
			tick = 1;
		}

		if (!strcmp(argv[start_arg], "--1rstwap")) {
			args.otherOper = WAP;
			tick = 1;
		}

		if (!strcmp(argv[start_arg], "--mbox")) {
			args.otherOper = IDEAMBOX;
			tick = 1;
		}

		if (!tick) break;
		start_arg++;
	}

	// aha, teraz juz tylko trzeba pobrac numer telefonu
	if (start_arg >= argc) return 1;
	else {
		char *addr_found = NULL;
#ifdef ADDR_BOOK
		addr_found = lookup_addrbook(argv[start_arg], args.telefon, sizeof(args.telefon)-1);
		debug_stream->Log(LOG_INFO, "Znaleziono w ksiazce adresowej: %s -> %s", argv[start_arg], args.telefon);
#endif
		// jesli nie znaleziono numeru w ksiazce telefonicznej...
		if (!addr_found) {
			strncpy(args.telefon, argv[start_arg], sizeof(args.telefon)-1);
		}
		args.telefon[sizeof(args.telefon)-1] = 0;
		start_arg++;
	}

	// teraz pobieramy tresc. jesli sa jeszcze jakies parametry, to
	// dodajemy je do tresci, jesli juz nie ma parametrow, to pobieramy
	// tresc ze stdin

	if (start_arg >= argc) {
		// pobieramy ze stdin
		strstream s;
		char *n;
		int len;

		cin >> s.rdbuf();
		len = s.pcount();
		n = s.str();
		strncpy(args.sms, (n) ? n : "", sizeof(args.sms)-1);
		if (len < sizeof(args.sms)) {
			args.sms[len] = 0;
		}
		s.freeze(0);
	} else {
		// pobieramy z linii polecen
		string msg;

		for(int i=start_arg; i<argc; i++)
			msg = msg + ((i>start_arg)?" ":"") + argv[i];
		strncpy(args.sms, msg.c_str(), sizeof(args.sms)-1);
	}

	args.sms[sizeof(args.sms)-1] = 0;

	return 0;
}


int main(int argc, char **argv)
{
    int status = 0;
    Targs args = {MAX_NSPLIT,0,"","","",0,0,""};

	memset(&konfig, 0, sizeof(konfig));
	debug_stream = new Debug(LOG_FILE);

#ifdef ADDR_BOOK
    // sprawdzimy czy wywolalismy program w trybie do operacji na ksiazce
    // adresowej
    {
        char *slash = strrchr(argv[0], '/');
        if (!strcmp(argv[0], SMSADDR) || (slash && !strcmp(slash+1, SMSADDR)))
           return addr_main(argc, argv);
    }
#endif

	// sprawdzamy jakie podano argumenty w linii polecen
	if (sprawdz_argumenty(argv, argc, args)) {
		fprintf(stderr, info_msg, VER, __TIME__, __DATE__, MAX_NSPLIT);
	#ifdef ADDR_BOOK
		fprintf(stderr, "Program skompilowano z obsluga ksiazki adresowej, zobacz takze: %s\n", SMSADDR);
	#endif        
		return 1;
	}

	// jesli explicite podano nazwe pliku konfiguracyjnego to odczytamy
	// konfiguracje tylko z niego
	odczytaj_konfig((*args.cfg) ? args.cfg : NULL);

	debug_stream->Log(LOG_INFO, "Odczytana konfiguracja:\n\tw3cache: %s:%d\n\tICQ UIN: %s\n\tICQ haslo: %s\n\tAdres email: %s\n\tPodpis: %s\n\tAdres notify: %s\n\tplus_mail: %d\n\tAdres IP: %s\n\tSUPERSMS USER: %s\n\tSUPERSMS PASS: %s\n\tIdea.czat login: %s\n\tIdea.czat haslo: %s\n\tIdea.czat adresat: %s\n\t1rstwap login: %s\n\t1rstwap haslo: %s\n\tidea_mbox login: %s\n\tidea_mbox pass: %s\n",
                             konfig.w3cache_host, konfig.w3cache_port, 
                             konfig.icq_uin, konfig.icq_pass, 
                             konfig.mailaddr, konfig.sign, konfig.notifyaddr, 
                             konfig.plus_mail, konfig.srcip, 
                             "", "",
                             konfig.czat_login, konfig.czat_pass, konfig.dlogin,
                             konfig.wap_login, konfig.wap_pass,
                             konfig.ideambox_login, konfig.ideambox_pass);

	if (args.check_ver) status = sprawdz_nowa_wersje();
	else if (args.thanksto) thanksto();
	else status = wyslij_sms(args);
	delete debug_stream;
	return konfig.no_error ? 0 : status;
}

int wyslij_sms(Targs &args) {
	int status = 0;
	SMS_packet sms;
        string sms_msg;
	
	if (!strlen(args.sms)) {
		debug_stream->Log(LOG_INFO, "Pusta wiadomosc, nie wysylam");
		return 0;
	};
    sms_msg = args.sms;
    if (strlen(konfig.sign)) sms_msg = sms_msg + " " + konfig.sign;
    debug_stream->Log(LOG_INFO, "Wiadomosc do wyslania: %s", sms_msg.c_str());

    try {
    sms_func gsm = NULL;
    int siec = ktora_siec(args.telefon);

    if (args.otherOper)
      siec=args.otherOper;

    if (siec != -1) {
        // instalujemy handler sygnalu alarmu
	signal(SIGALRM, sig_alarm);
	alarm(ALARM);

	sms.telefon = args.telefon;
	sms.wiadomosc = (char*)(sms_msg.c_str());
	sms.potwierdzenie = GSM_Oper[siec].ok_msg;
	sms.nsplit = args.nsplit;
	sms.max_len = GSM_Oper[siec].max_len;
	gsm = GSM_Oper[siec].gsm;

	if (!gsm) throw new Exception("Niezdefiniowana funkcja wysylajaca");
	else if (!WyslijSMS(gsm, &sms)) {
		status = SMS_OK;
		debug_stream->Log(LOG_INFO, "Otrzymano potwierdzenie wyslania wiadomosci");
	} else {
		debug_stream->Log(LOG_INFO, "Nie otrzymano potwierdzenie wyslania wiadomosci");
		throw new Exception("Nie otrzymano potwierdzenia wyslania wiadomosci");
	}

	alarm(0);
    } else {
	if (!konfig.quiet) cerr <<  "Nie wiem jak wyslac SMS na numer " << args.telefon << endl;
	status=SMS_FATAL;
    }
    }

    catch (Exception *exc) {
         if (!konfig.quiet) cerr << "sms: " << exc->Info() << endl;
         status=SMS_SOFTERR;
    }
    return status;
}

int ktora_siec(const char *nr)
{
#ifdef DEBUG
    if (!strcmp(nr, "000")) return TEST;
#endif
    if (*nr == '5') return IDEAMBOX;
    if (*nr == '8') return ERA_GSM; 	// Heyah
    if (*nr == '6') {
       if ((nr[2] - '0') % 2) return PLUS_GSM;
       else return ERA_GSM;
    }
    return -1;
}

void odczytaj_konfig(const char *cfg) {
	char file[MAXPATHLEN], line[256], *c, *path;
	struct passwd *pwd;
	struct stat st;
	FILE *f;

	if (!cfg) {
		// najpierw odczytamy ew. dane ze zmiennych srodowiska
	        if (!(c = getenv("http_proxy"))) c = getenv("HTTP_PROXY");
		if (c) odczytaj_w3cache(c);
		
		// najpierw odczytujemy globalny plik konfiguracyjny
		odczytaj_konfig(SMS_RC);
		
		// potem z katalogu uzytkownika
		if (pwd = getpwuid(getuid())) {
			// jesli jest zdefiniowana zmienna config_dir,
			// to z niej odczytujemy katalog z plikami konf
			if ((path = getenv("CONFIG_DIR")) && *path)
				snprintf(file, sizeof(file)-1,"%s/%s/smsrc", pwd->pw_dir, path);
			// jesli nie bylo zdefiniowanej zmiennej
			// config_dir, badz w katalogu przez nia
			// wskazywanym nie bylo pliku konf to bierzemy
			// domyslny plik konf
			if (!path || stat(path,&st)==-1)
				snprintf(file, sizeof(file)-1,"%s/.smsrc", pwd->pw_dir);
			odczytaj_konfig(file);
		}

		// jesli nie odczytano danych o koncie w usludzie Idea.czat
		// to bierzemy wartosci domyslne
		if (!konfig.czat_login) {
			strcpy(konfig.czat_login, CZAT_LOGIN);
			strcpy(konfig.czat_pass, CZAT_PASS);
		}

		// analogicznie dla Omnixa
		if (!konfig.omnix_login) {
			strcpy(konfig.omnix_login, OMNIX_LOGIN);
			strcpy(konfig.omnix_pass, OMNIX_PASS);
		}

		// ... i dla www.1rstwap.com
		if (!konfig.wap_login) {
			strcpy(konfig.wap_login, WAP_LOGIN);
			strcpy(konfig.wap_pass, WAP_PASS);
		}
		// MiastoPlusa
		if (!konfig.mplusa_login) {
			strcpy(konfig.mplusa_login, MPLUSA_LOGIN);
			strcpy(konfig.mplusa_pass, MPLUSA_PASS);
		}
		// IDEA mBox
		if (!konfig.ideambox_login) {
			strcpy(konfig.ideambox_login, IDEAMBOX_LOGIN);
			strcpy(konfig.ideambox_pass, IDEAMBOX_PASS);
		}
	} else {
		// cfg wskazuje na plik konfiguracyjny do odczytania
		if (f = fopen(cfg, "r")) {
			while (fgets(line, sizeof(line)-1, f)) {
				// pomijamy komentarze
				if (*line=='#') continue;
				if (c = strchr(line, '\n')) *c = 0;
				// jesli znaleziono znak '='
				if (c = strchr(line, '=')) {
					*c = 0;
					c++;
					if (!strcmp(line,"proxy")) 
						odczytaj_w3cache(c);
					if (!strcmp(line,"icq_uin"))
						strncpy(konfig.icq_uin, c, sizeof(konfig.icq_uin)-1);
					if (!strcmp(line,"icq_pass"))
						strncpy(konfig.icq_pass, c, sizeof(konfig.icq_pass)-1);
					if (!strcmp(line,"mailaddr"))
						strncpy(konfig.mailaddr, c, sizeof(konfig.mailaddr)-1);
					if (!strcmp(line,"notifyaddr"))
						strncpy(konfig.notifyaddr, c, sizeof(konfig.notifyaddr)-1);
					if (!strcmp(line,"plus_mail"))
						konfig.plus_mail = atoi(c);
					if (!strcmp(line,"src_ip"))
                                                strncpy(konfig.srcip, c, sizeof(konfig.srcip)-1);
					if (!strcmp(line,"signature"))
						strncpy(konfig.sign, c, sizeof(konfig.sign)-1);
					if (!strcmp(line,"czat_login"))
						strncpy(konfig.czat_login, c, sizeof(konfig.czat_login)-1);
					if (!strcmp(line, "czat_pass"))
						strncpy(konfig.czat_pass, c, sizeof(konfig.czat_pass)-1);
                                        if (!strcmp(line,"omnix_user"))
                                                        strncpy(konfig.omnix_login, c, sizeof(konfig.omnix_login)-1);
                                        if (!strcmp(line,"omnix_pass"))
                                                        strncpy(konfig.omnix_pass, c, sizeof(konfig.omnix_pass)-1);
                                        if (!strcmp(line,"wap_login"))
	                                                strncpy(konfig.wap_login, c, sizeof(konfig.wap_login)-1);
                                        if (!strcmp(line,"wap_pass"))
	                                                strncpy(konfig.wap_pass, c, sizeof(konfig.wap_pass)-1);
                                        if (!strcmp(line,"miastoplusa_user"))
	                                                strncpy(konfig.mplusa_login, c, sizeof(konfig.mplusa_login)-1);
                                        if (!strcmp(line,"miastoplusa_pass"))
	                                                strncpy(konfig.mplusa_pass, c, sizeof(konfig.mplusa_pass)-1);
                                        if (!strcmp(line,"ideambox_login"))
	                                                strncpy(konfig.ideambox_login, c, sizeof(konfig.ideambox_login)-1);
                                        if (!strcmp(line,"ideambox_pass"))
	                                                strncpy(konfig.ideambox_pass, c, sizeof(konfig.ideambox_pass)-1);
				}
				
			}
			fclose(f);
		}
	}
	
}

void odczytaj_w3cache(char *w3c)
{
        char *c;

        // proste sprawdzenie czy pobrany string pasuje do naszego formatu
        if (strncmp(w3c, "http", 4)) return;

        w3c = w3c + 7;
        if (!(c = strchr(w3c, ':'))) return;

        *(c++) = 0;

        strcpy(konfig.w3cache_host, w3c);
        konfig.w3cache_port = atoi(c);
}

int sprawdz_nowa_wersje() {
	int status = 1;
	HTTP_Request *s = new HTTP_Request("ceti.pl", 80,
			konfig.w3cache_host, konfig.w3cache_port);

	delete s->GetData("/~miki/komputery/download/sms/VERSION", 1);
	const char *new_ver = s->GetBody();
	// teraz w new_ver mamy wszystko co dostalismy od serwera, razem
	// z naglowkami
	const char *last_nl = new_ver+strlen(new_ver)-strlen(VER);
	while (last_nl>new_ver && isgraph(*last_nl)) last_nl--;

	last_nl++;

	char *ver = strdup(last_nl);
	char *ver2 = ver;
	while (*ver2 && isgraph(*ver2)) ver2++;
	*ver2 = 0;

	if (strlen(VER) != strlen(ver) || strncmp(VER, ver, strlen(VER))) {
		status = 0;
		if (!konfig.quiet) cout << "Jest dostepna nowa wersja programu." << endl;
	}
	
	free(ver);
	delete s;
	return status;
}

void thanksto() {
	cout << 
"Ponizsze osoby przycznily sie do rozwoju programu, badz przez zakodowanie\n"\
"nowego modulu, zakodowanie skryptu, badz poprzez swoje (konstruktywne) uwagi\n"\
"lub wytkniecie bledow. Lista pewnie nie jest kompletna, ale coz, pamiec ludzka\n"\
"jest zawodna ;-)\n\n"\
"Piotr Godowski, <flash@v-lo.krakow.pl>\n"\
"Michal Kowalczuk, <sammael@brzydal.eu.org>\n"\
"Bartek Sawicki\n"\
"Marcin Owsiany <marcin@owsiany.pl>\n"\
"Marian Witkowski <marian@witkowscy.com>\n"\
"Andrzej Oszer <oszer@poczta.onet.pl>\n"\
"Marcin Labuda <martin@asm.gda.pl>\n"\
"Marcin Przadlo <M.Przadlo@elka.pw.edu.pl>\n"\
"Witold Wilczynski <madman@linux.bydg.org>\n"\
"Rafal Kupka\n"\
"Tomasz Paszkowski <tpaszkowski@online.pl>\n"\
"Kamil Andrusz\n"\
"Dariusza Wrebiak\n"\
"Radoslaw Zielinski\n"\
"Pawel Kot\n"\
"Cyprian Zawadzki\n"\
"Tomasz Luchowski\n"\
"Mariusz Zynel\n"\
"Pawel Kierski <pkierski@mks.com.pl>\n"\
"Grzegorz Nowak <axe@smars.pl>\n"\
"Tomasz Olszewski <caster@3miasto.net>\n"\
"Michal Margula <alchemyx@uznam.net.pl>\n"\
"Jarek Wrzesien <wrzesien@poland.com>\n"\
"Piotr Milcarz <piotrek@smsnews.org>\n"\
"Bartek Sowa <bartowl@dione.ids.pl>\n"\
"Rafal Wijata <raven@cavern.pl>\n"\
"Piotr Budny <vip@linux.pl>\n"\
"Dariusz Sznajder\n"\
"Jakub Klausa\n"\
"Lukasz Wojtow <Lukasz.Wojtow@euromedia.pl>\n"
"Krzysztof Jan Stencel <stencel@mimuw.edu.pl>\n"\
"Tomasz Orzechowski <orzech@pld.org.pl>\n"\
"Piotr Maj <piotr.maj@kernelpanic.pl>\n"\
"Arkadiusz Wahlig <yak@yak.prv.pl>\n"\
"Krzysztof Malisiewicz <kiniu@agatka.math.uni.wroc.pl>\n"\
"Marek Szyprowski <march@staszic.waw.pl>\n"\
"Maciej Witkowiak <ytm@elysium.pl>\n" \
"Jakub Pidel <qbic@staszic.waw.pl>\n" \
"Marek Majchrowski <majherek@pc-4.chomiczowka.waw.pl>\n" \
"Adrian Siemieniak <sauron@rpg.pl>\n"\
"\nJesli nie chcesz byc wylistowany na ww liscie daj mi znac ;-)\n" << std::endl;
}

#ifdef DEBUG
// a to jest tylko do testowania na wlasnym serwerze www - w dystrybucji
// znajduje sie odpowiednia strona html i skrypt cgi do ktorej ta
// funkcja sie odwoluje
int WyslijSMS_Test(SMS_packet *sms)
{
	char *t = sms->telefon;
	char *w = sms->wiadomosc;
	char *ok = sms->potwierdzenie;
	int ret_val;
	HTTP_Request *s = new HTTP_Request("localhost", 80,
					konfig.w3cache_host, konfig.w3cache_port);

	s->AddHeader("Host","localhost");

	Headers *form = new Headers();

	form->Add("numer", t);
	form->Add("tekst", w);

	delete s->PostData("/~miki/cgi-bin/test-sms.cgi", *form);

	// sprawdzimy co otrzymalismy w odpowiedzi od serwera
	ret_val = poprawna_odpowiedz(ok, t, s->GetBody());

	delete form;
	delete s;

	return ret_val;
}
#endif