1 /*
2  * Tlf - contest logging program for amateur radio operators
3  * Copyright (C) 2001-2002-2003 Rein Couperus <pa0rct@amsat.org>
4  *               2013           Ervin Hegedüs - HA2OS <airween@gmail.com>
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2 of the License, or
9  * (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software
18  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
19  */
20 
21 /* ------------------------------------------------------------
22  *      add call/band to dupe list
23  *
24  *--------------------------------------------------------------*/
25 #ifndef _GNU_SOURCE
26 #define _GNU_SOURCE
27 #endif
28 
29 #ifndef _XOPEN_SOURCE
30 #define _XOPEN_SOURCE
31 #endif
32 
33 #include <stdlib.h>
34 #include <string.h>
35 
36 #include <glib.h>
37 #include <time.h>
38 
39 #include "addcall.h"
40 #include "addmult.h"
41 #include "addpfx.h"
42 #include "bands.h"
43 #include "dxcc.h"
44 #include "getctydata.h"
45 #include "getpx.h"
46 #include "get_time.h"
47 #include "log_utils.h"
48 #include "paccdx.h"
49 #include "score.h"
50 #include "searchcallarray.h"
51 #include "tlf.h"
52 #include "zone_nr.h"
53 
54 int excl_add_veto;
55 /* This variable helps to handle in other modules, that station is multiplier
56  * or not */
57 /* In addcall2(), this variable helps to handle the excluded multipliers,
58  * which came from lan_logline the Tlf scoring logic is totally completely
59  * different in local and LAN source the addcall() function doesn't increment
60  * the band_score[] array, that maintains the score() function. Here, the
61  * addcall2() is need to separate the points and multipliers.
62  */
63 
addcall(void)64 int addcall(void) {
65     extern char hiscall[];
66     extern int nr_worked;
67     extern struct worked_t worked[];
68     extern char comment[];
69     extern int cqww;
70     extern int bandinx;
71     extern int countries[MAX_DATALINES];
72     extern int zones[];
73     extern int countryscore[];
74     extern int addcty;
75     extern int zonescore[];
76     extern int addzone;
77     extern int countrynr;
78     extern int arrldx_usa;
79     extern int pacc_pa_flg;
80     extern int universal;
81     extern int country_mult;
82     extern int w_cty;
83     extern int ve_cty;
84     extern int dx_arrlsections;
85     extern int wazmult;
86     extern int itumult;
87     extern char pxstr[];
88     extern t_pfxnummulti pfxnummulti[MAXPFXNUMMULT];
89     extern int pfxnummultinr;
90     extern int addcallarea;
91     extern bool continentlist_only;
92     extern char continent[];
93     extern int exclude_multilist_type;
94     extern int trxmode;
95     extern struct tm *time_ptr;
96 
97     static int found = 0;
98     static int i, j, z = 0;
99     static int add_ok;
100     int pfxnumcntidx = -1;
101     int pxnr = 0;
102     excl_add_veto = 0;
103 
104     get_time();
105 
106     found = searchcallarray(hiscall);
107 
108     if (found == -1) {
109 
110 	i = nr_worked;
111 	g_strlcpy(worked[i].call, hiscall, 20);
112 	nr_worked++;
113     } else
114 	i = found;
115 
116     worked[i].qsotime[trxmode][bandinx] = (long)mktime(time_ptr);
117     j = getctydata(hiscall);
118     worked[i].country = j;
119     if (strlen(comment) >= 1) {		/* remember last exchange */
120 	strcpy(worked[i].exchange, comment);
121 
122 	if ((cqww == 1) || (wazmult == 1) || (itumult == 1)) {
123 	    /*
124 	    			if (strlen(zone_fix) > 1) {
125 	    				z = zone_nr(zone_fix);
126 	    			} else
127 	    				z = zone_nr(zone_export);
128 	    */
129 	    z = zone_nr(comment);
130 
131 	}
132     }
133 
134     add_ok = 1;			/* look if certain calls are excluded */
135 
136     if ((arrldx_usa == 1)
137 	    && ((countrynr == w_cty) || (countrynr == ve_cty)))
138 	add_ok = 0;
139 
140     if ((country_mult == 1) && (universal == 1))
141 	add_ok = 1;
142 
143     if ((dx_arrlsections == 1)
144 	    && ((countrynr == w_cty) || (countrynr == ve_cty)))
145 	add_ok = 0;
146 
147     if (pacc_pa_flg == 1)
148 	add_ok = pacc_pa();
149 
150     // if pfx number as multiplier
151     if (pfxnummultinr > 0) {
152 	getpx(hiscall);
153 	pxnr = pxstr[strlen(pxstr) - 1] - 48;
154 
155 	int pfxi = 0;
156 	while (pfxi < pfxnummultinr) {
157 	    if (pfxnummulti[pfxi].countrynr == j) {
158 		pfxnumcntidx = pfxi;
159 		break;
160 	    }
161 	    pfxi++;
162 	}
163     }
164 
165     if (continentlist_only) {
166 	if (!is_in_continentlist(continent)) {
167 	    add_ok = 0;
168 	    addcty = 0;
169 	    addcallarea = 0;
170 	    excl_add_veto = 1;
171 	}
172     }
173 
174     if (!continentlist_only
175 	    && exclude_multilist_type == EXCLUDE_CONTINENT) {
176 	if (is_in_continentlist(continent)) {
177 	    add_ok = 0;
178 	    addcty = 0;
179 	    addcallarea = 0;
180 	    excl_add_veto = 1;
181 	}
182     }
183 
184     if (exclude_multilist_type == EXCLUDE_COUNTRY) {
185 	if (is_in_countrylist(j)) {
186 	    add_ok = 0;
187 	    addcty = 0;
188 	    addcallarea = 0;
189 	    excl_add_veto = 1;
190 	}
191     }
192 
193     if (add_ok == 1) {
194 
195 	worked[i].band |= inxes[bandinx];	/* worked on this band */
196 
197 	switch (bandinx) {
198 
199 	    case BANDINDEX_160:
200 	    case BANDINDEX_80:
201 	    case BANDINDEX_40:
202 	    case BANDINDEX_20:
203 	    case BANDINDEX_15:
204 	    case BANDINDEX_10:
205 
206 		if (pfxnumcntidx < 0) {
207 		    if (j != 0 && (countries[j] & inxes[bandinx]) == 0) {
208 			countries[j] |= inxes[bandinx];
209 			countryscore[bandinx]++;
210 			addcty = j;
211 		    }
212 		    if (z != 0 && (zones[z] & inxes[bandinx]) == 0) {
213 			zones[z] |= inxes[bandinx];
214 			zonescore[bandinx]++;
215 			addzone = z;
216 		    }
217 		} else {
218 		    if ((pfxnummulti[pfxnumcntidx].qsos[pxnr] & inxes[bandinx])
219 			    == 0) {
220 			pfxnummulti[pfxnumcntidx].qsos[pxnr] |= inxes[bandinx];
221 			addcallarea = 1;
222 			countryscore[bandinx]++;
223 			zonescore[bandinx]++;
224 		    }
225 		}
226 		break;
227 
228 
229 	    case BANDINDEX_12:
230 	    case BANDINDEX_17:
231 	    case BANDINDEX_30:
232 
233 		if (j != 0 && (countries[j] & inxes[bandinx]) == 0) {
234 		    countries[j] |= inxes[bandinx];
235 		    addcty = j;
236 		}
237 		if (z != 0 && (zones[z] & inxes[bandinx]) == 0) {
238 		    zones[z] |= inxes[bandinx];
239 		    addzone = z;
240 		}
241 		break;
242 
243 	}
244     }
245 
246     addmult();			/* for wysiwyg */
247 
248     return j;
249 }
250 
251 /* ----------------------for network qso's-----------------------------------*/
252 
addcall2(void)253 int addcall2(void) {
254 
255     extern int nr_worked;
256     extern struct worked_t worked[];
257     extern int cqww;
258     extern int countries[MAX_DATALINES];
259     extern int zones[];
260     extern int countryscore[];
261     extern int zonescore[];
262     extern int pacc_pa_flg;
263     extern int universal;
264     extern int country_mult;
265     extern char lan_logline[];
266     extern int band_score[];
267     extern int wpx;
268     extern int wazmult;
269     extern int itumult;
270     extern char pxstr[];
271     extern t_pfxnummulti pfxnummulti[MAXPFXNUMMULT];
272     extern int pfxnummultinr;
273     extern int addcallarea;
274     extern int countrynr;
275     extern bool continentlist_only;
276     extern char continent[];
277 
278     extern int pfxmultab;
279     extern int exclude_multilist_type;
280     extern int trxmode;
281 
282     int found = 0;
283     int i, j, p, z = 0;
284     int add_ok;
285     char lancopy[6];
286 
287     char hiscall[20];
288     char comment[40];
289     int bandinx;
290     int pfxnumcntidx = -1;
291     int pxnr = 0;
292     excl_add_veto = 0;
293     char date_and_time[16];
294     struct tm qsotime;
295     time_t qsotimets;
296 
297     g_strlcpy(hiscall, lan_logline + 29, 20);
298     *strchrnul(hiscall, ' ') = '\0';	/* terminate on first blank */
299 
300     g_strlcpy(comment, lan_logline + 54, 31);
301     *strchrnul(comment, ' ') = '\0';	/* terminate on first blank */
302 
303     /* FIXME: worked array needs mutex protection */
304     found = searchcallarray(hiscall);
305 
306     if (found == -1) {
307 
308 	i = nr_worked;
309 	g_strlcpy(worked[i].call, hiscall, 20);
310 	nr_worked++;
311     } else
312 	i = found;
313 
314     j = getctynr(hiscall);
315 
316     bandinx = log_get_band(lan_logline);
317 
318     /* calculate QSO timestamp from lan_logline */
319     memset(&qsotime, 0, sizeof(struct tm));
320     strncpy(date_and_time, lan_logline + 7, 15);
321     strptime(date_and_time, "%d-%b-%y %H:%M", &qsotime);
322     qsotimets = mktime(&qsotime);
323 
324     worked[i].qsotime[trxmode][bandinx] = qsotimets;
325     worked[i].country = j;
326     if (strlen(comment) >= 1) {
327 //              strcpy(worked[i].exchange,comment);
328 
329 	if ((cqww == 1) || (wazmult == 1) || (itumult == 1))
330 	    z = zone_nr(comment);
331     }
332 
333     add_ok = 1;			/* look if certain calls are excluded */
334 
335     /* 	     if ((arrldx_usa ==1) && ((j == w_cty) || (j == ve_cty)))
336      	     	add_ok = 0;
337     */
338     if ((country_mult == 1) && (universal == 1))
339 	add_ok = 1;
340 
341     if (pacc_pa_flg == 1)
342 	/* FIXME: Does not work for LAN qso's as pacc_pa uses global variables
343 	 * set from foreground task */
344 	add_ok = pacc_pa();
345 
346     // if pfx number as multiplier
347     if (pfxnummultinr > 0) {
348 	getpx(hiscall);		/* FIXME: uses global 'pxstr' for background
349 				   job */
350 	pxnr = pxstr[strlen(pxstr) - 1] - 48;
351 
352 	int pfxi = 0;
353 	while (pfxi < pfxnummultinr) {
354 	    if (pfxnummulti[pfxi].countrynr == j) {
355 		pfxnumcntidx = pfxi;
356 		break;
357 	    }
358 	    pfxi++;
359 	}
360 	add_ok = 1;
361     }
362 
363 
364     if (continentlist_only) {
365 	if (!is_in_continentlist(dxcc_by_index(j)->continent)) {
366 	    excl_add_veto = 1;
367 	}
368     }
369 
370     if (!continentlist_only
371 	    && exclude_multilist_type == EXCLUDE_CONTINENT) {
372 	if (is_in_continentlist(dxcc_by_index(j)->continent)) {
373 	    excl_add_veto = 1;
374 	}
375     }
376 
377     if (exclude_multilist_type == EXCLUDE_COUNTRY) {
378 	if (is_in_countrylist(j)) {
379 	    excl_add_veto = 1;
380 	}
381     }
382 
383     if (add_ok == 1) {
384 
385 	bandinx = log_get_band(lan_logline);
386 	band_score[bandinx]++;
387 
388 	worked[i].band |= inxes[bandinx];	/* worked on this band */
389 
390 	if (excl_add_veto == 0) {
391 
392 	    switch (bandinx) {
393 
394 		case BANDINDEX_160:
395 		case BANDINDEX_80:
396 		case BANDINDEX_40:
397 		case BANDINDEX_20:
398 		case BANDINDEX_15:
399 		case BANDINDEX_10:
400 
401 		    if (pfxnumcntidx < 0) {
402 			if (j != 0 && (countries[j] & inxes[bandinx]) == 0) {
403 			    countries[j] |= inxes[bandinx];
404 			    countryscore[bandinx]++;
405 //                              addcty = j;
406 			}
407 			if (z != 0 && (zones[z] & inxes[bandinx]) == 0) {
408 			    zones[z] |= inxes[bandinx];
409 			    zonescore[bandinx]++;
410 //                              addzone = z;
411 			}
412 		    } else {
413 			if ((pfxnummulti[pfxnumcntidx].qsos[pxnr] & BAND10) == 0) {
414 			    pfxnummulti[pfxnumcntidx].qsos[pxnr] |= inxes[bandinx];
415 			    addcallarea = 1;
416 			    zonescore[bandinx]++;
417 			    countryscore[bandinx]++;
418 			}
419 		    }
420 		    break;
421 
422 		case BANDINDEX_30:
423 		case BANDINDEX_17:
424 		case BANDINDEX_12:
425 
426 		    if (j != 0 && (countries[j] & inxes[bandinx]) == 0) {
427 			countries[j] |= inxes[bandinx];
428 		    }
429 		    if (z != 0 && (zones[z] & inxes[bandinx]) == 0) {
430 			zones[z] |= inxes[bandinx];
431 		    }
432 		    break;
433 
434 	    }
435 	}
436     }
437     if (wpx == 1 || pfxmultab == 1) {
438 
439 	if (lan_logline[68] != ' ') {
440 
441 	    strcpy(lancopy, "     ");
442 
443 	    /* max 5 char for prefix written in makelogline */
444 	    strncpy(lancopy, lan_logline + 68, 5);
445 
446 	    for (p = 0; p <= 5; p++) {	// terminate at first space
447 
448 		if (lancopy[p] == ' ') {
449 		    lancopy[p] = '\0';
450 		    break;
451 		}
452 	    }
453 
454 	    bandinx = log_get_band(lan_logline);
455 
456 	    add_pfx(lancopy, bandinx);
457 	}
458     }
459 
460     addmult2();			/* for wysiwyg from LAN */
461 
462     return j;
463 }
464 
465