1 #define _GNU_SOURCE /* For strcasestr */
2 #include <string.h>
3 
4 #include "../helper/locales.h"
5 
6 #include <gammu.h>
7 #include <stdlib.h>
8 #include <ctype.h>
9 
10 #ifdef GSM_ENABLE_NOKIA_DCT3
11 #  include "depend/nokia/dct3.h"
12 #  include "depend/nokia/dct3trac/wmx.h"
13 #endif
14 #ifdef GSM_ENABLE_NOKIA_DCT4
15 #  include "depend/nokia/dct4.h"
16 #endif
17 
18 #include "nokia.h"
19 #include "common.h"
20 #include "files.h"
21 
22 #include "../helper/formats.h"
23 #include "../helper/printing.h"
24 #include "../libgammu/misc/string.h"
25 
26 #if defined(GSM_ENABLE_NOKIA_DCT3) || defined(GSM_ENABLE_NOKIA_DCT4)
NokiaComposer(int argc UNUSED,char * argv[])27 void NokiaComposer(int argc UNUSED, char *argv[])
28 {
29 	GSM_Error error;
30 	GSM_Ringtone 		ringtone;
31 	gboolean			started;
32 	int 			i,j;
33 	GSM_RingNote 		*Note;
34 	GSM_RingNoteDuration 	Duration;
35 	GSM_RingNoteDuration 	DefNoteDuration = 32; /* 32 = Duration_1_4 */
36 	unsigned int		DefNoteScale 	= Scale_880;
37 
38 	ringtone.Format	= 0;
39 	error=GSM_ReadRingtoneFile(argv[2],&ringtone);
40 	Print_Error(error);
41 
42 	if (ringtone.Format != RING_NOTETONE) {
43 		printf("%s\n", _("It can be RTTL ringtone only used with this option"));
44 		Terminate(2);
45 	}
46 
47 	started = FALSE;
48 	j	= 0;
49 	for (i=0;i<ringtone.NoteTone.NrCommands;i++) {
50 		if (ringtone.NoteTone.Commands[i].Type == RING_Note) {
51 			Note = &ringtone.NoteTone.Commands[i].Note;
52 			if (!started) {
53 				if (Note->Note != Note_Pause) {
54 					printf(_("Ringtone \"%s\" (tempo = %i Beats Per Minute)"),DecodeUnicodeConsole(ringtone.Name),GSM_RTTLGetTempo(Note->Tempo));
55 					printf("\n\n");
56 					started = TRUE;
57 				}
58 			}
59 			if (started) j++;
60 		}
61 	}
62     	if (j>50) {
63 		printf_warn(_("length=%i notes, but you will enter only first 50 tones."), j);
64 	}
65 
66 	printf("\n\n%s ", _("This ringtone in Nokia Composer in phone should look:"));
67 	started = FALSE;
68 	for (i=0;i<ringtone.NoteTone.NrCommands;i++) {
69 		if (ringtone.NoteTone.Commands[i].Type == RING_Note) {
70 			Note = &ringtone.NoteTone.Commands[i].Note;
71 			if (!started) {
72 				if (Note->Note != Note_Pause) started = TRUE;
73 			}
74 			if (started) {
75 				switch (Note->Duration) {
76 					case Duration_INVALID: break;
77 					case Duration_Full: printf("1"); break;
78 					case Duration_1_2 : printf("2"); break;
79 					case Duration_1_4 : printf("4"); break;
80 					case Duration_1_8 : printf("8"); break;
81 					case Duration_1_16: printf("16");break;
82 					case Duration_1_32: printf("32");break;
83 				}
84 				if (Note->DurationSpec == DottedNote) printf(".");
85 				switch (Note->Note) {
86 					case Note_INVALID: break;
87 					case Note_C  	: printf("c");	break;
88 					case Note_Cis	: printf("#c");	break;
89 					case Note_D  	 :printf("d");	break;
90 					case Note_Dis	: printf("#d");	break;
91 					case Note_E  	: printf("e");	break;
92 					case Note_F  	: printf("f");	break;
93 					case Note_Fis	: printf("#f");	break;
94 					case Note_G  	: printf("g");	break;
95 					case Note_Gis	: printf("#g");	break;
96 					case Note_A  	: printf("a");	break;
97 					case Note_Ais	: printf("#a");	break;
98 					case Note_H  	: printf("h");	break;
99 					case Note_Pause : printf("-");	break;
100 				}
101 				if (Note->Note != Note_Pause) printf("%i",Note->Scale - 4);
102 				printf(" ");
103 			}
104 		}
105 	}
106 
107 	printf("\n\n%s ", _("To enter it please press:"));
108 	started = FALSE;
109 	for (i=0;i<ringtone.NoteTone.NrCommands;i++) {
110 		if (ringtone.NoteTone.Commands[i].Type == RING_Note) {
111 			Note = &ringtone.NoteTone.Commands[i].Note;
112 			if (!started) {
113 				if (Note->Note != Note_Pause) started = TRUE;
114 			}
115 			if (started) {
116 				switch (Note->Note) {
117 	      				case Note_C  : case Note_Cis:	printf("1");break;
118 	      				case Note_D  : case Note_Dis:	printf("2");break;
119 	      				case Note_E  :			printf("3");break;
120 	      				case Note_F  : case Note_Fis:	printf("4");break;
121 	      				case Note_G  : case Note_Gis:	printf("5");break;
122 	      				case Note_A  : case Note_Ais:	printf("6");break;
123 	      				case Note_H  :			printf("7");break;
124 	      				default      :			printf("0");break;
125 				}
126 				if (Note->DurationSpec == DottedNote) printf("%s", _("(longer)"));
127 	    			switch (Note->Note) {
128       					case Note_Cis: case Note_Dis:
129       					case Note_Fis: case Note_Gis:
130       					case Note_Ais:
131 						printf("#");
132 						break;
133       					default      :
134 						break;
135     				}
136 				if (Note->Note != Note_Pause) {
137 					if ((unsigned int)Note->Scale != DefNoteScale) {
138 						while (DefNoteScale != (unsigned int)Note->Scale) {
139 							printf("*");
140 							DefNoteScale++;
141 							if (DefNoteScale==Scale_7040) DefNoteScale = Scale_880;
142 						}
143 					}
144 				}
145 				Duration = 0;
146 				switch (Note->Duration) {
147 					case Duration_Full : Duration = 128;	break;
148 					case Duration_1_2  : Duration = 64;	break;
149 					case Duration_1_4  : Duration = 32;	break;
150 					case Duration_1_8  : Duration = 16;	break;
151 					case Duration_1_16 : Duration = 8;	break;
152 					case Duration_1_32 : Duration = 4;	break;
153 					default		   : fprintf(stderr, "error\n");break;
154 				}
155 				if (Duration > DefNoteDuration) {
156 		        		while (DefNoteDuration != Duration) {
157 						printf("9");
158 			  			DefNoteDuration = DefNoteDuration * 2;
159 					}
160 			      	}
161 				if (Duration < DefNoteDuration) {
162 		        		while (DefNoteDuration != Duration) {
163 						printf("8");
164 			  			DefNoteDuration = DefNoteDuration / 2;
165 					}
166 			      	}
167 				printf(" ");
168 			}
169 		}
170 	}
171 
172 	printf("\n");
173 	fflush(stdout);
174 }
175 
NokiaSecurityCode(int argc,char * argv[])176 void NokiaSecurityCode(int argc, char *argv[])
177 {
178 	GSM_Init(TRUE);
179 
180 #ifdef GSM_ENABLE_NOKIA_DCT3
181 	if (CheckDCT3Only() != ERR_NOTSUPPORTED) {
182 		DCT3GetSecurityCode(argc,argv);
183 	}
184 #endif
185 #ifdef GSM_ENABLE_NOKIA_DCT4
186 	if (CheckDCT4Only() != ERR_NOTSUPPORTED) {
187 	/* 	DCT4ResetSecurityCode(argc, argv); */
188 		DCT4GetSecurityCode(argc,argv);
189 	}
190 #endif
191 
192 	GSM_Terminate();
193 }
194 
NokiaSetPhoneMenus(int argc,char * argv[])195 void NokiaSetPhoneMenus(int argc, char *argv[])
196 {
197 	GSM_Init(TRUE);
198 
199 #ifdef GSM_ENABLE_NOKIA_DCT3
200 	if (CheckDCT3Only() != ERR_NOTSUPPORTED) {
201 		DCT3SetPhoneMenus (argc, argv);
202 	}
203 #endif
204 #ifdef GSM_ENABLE_NOKIA_DCT4
205 	if (CheckDCT4Only() != ERR_NOTSUPPORTED) {
206 		DCT4SetPhoneMenus (argc, argv);
207 	}
208 #endif
209 
210 	GSM_Terminate();
211 }
212 
NokiaSelfTests(int argc,char * argv[])213 void NokiaSelfTests(int argc, char *argv[])
214 {
215 	GSM_Init(TRUE);
216 
217 #ifdef GSM_ENABLE_NOKIA_DCT3
218 	if (CheckDCT3Only() != ERR_NOTSUPPORTED) {
219 		DCT3SelfTests(argc, argv);
220 	}
221 #endif
222 #ifdef GSM_ENABLE_NOKIA_DCT4
223 	if (CheckDCT4Only() != ERR_NOTSUPPORTED) {
224 		DCT4SelfTests(argc, argv);
225 	}
226 #endif
227 
228 	GSM_Terminate();
229 }
230 
231 typedef struct _PlayListEntry PlayListEntry;
232 
233 struct _PlayListEntry {
234 	unsigned char		*Name;
235 	unsigned char		*NameUP;
236 	PlayListEntry		*Next;
237 };
238 
NokiaAddPlayLists2(unsigned char * ID,unsigned char * Name,unsigned char * IDFolder)239 void NokiaAddPlayLists2(unsigned char *ID,unsigned char *Name,unsigned char *IDFolder)
240 {
241 	GSM_Error error;
242 	gboolean 			Start = TRUE, Available = FALSE;
243 	GSM_File	 	Files,Files2,Files3;
244 	int 			j,NamesPos2=0;
245 	size_t i, NamesPos = 0;
246 	unsigned char		Buffer[20],Buffer2[500];
247 	unsigned char		*Names,*Names2,*Pointer;
248 	PlayListEntry		*First,*Entry=NULL,*Prev;
249 
250 	First = NULL; Names=NULL; Names2=NULL;
251 
252 	CopyUnicodeString(Files.ID_FullName,ID);
253 
254 	printf(_("Checking %s\n"),DecodeUnicodeString(Name));
255 	/* looking into folder content (searching for mp3 and similiar) */
256 	while (1) {
257 		error = GSM_GetFolderListing(gsm,&Files,Start);
258 		if (error == ERR_FOLDERPART) {
259 			printf("%s\n", _("  Only part handled!"));
260 			break;
261 		}
262 		if (error == ERR_EMPTY) {
263 			break;
264 		}
265 		if (error == ERR_FILENOTEXIST) {
266 			goto out;
267 		}
268 	    	Print_Error(error);
269 
270 		if (!Files.Folder) {
271 			if (strcasestr(DecodeUnicodeConsole(Files.Name),".mp3")!=NULL ||
272 			    strcasestr(DecodeUnicodeConsole(Files.Name),".aac")!=NULL) {
273 				if (First==NULL) {
274 					First = malloc(sizeof(PlayListEntry));
275 					Entry = First;
276 				} else {
277 					Entry->Next = malloc(sizeof(PlayListEntry));
278 					Entry = Entry->Next;
279 				}
280 				Entry->Next = NULL;
281 				Entry->Name = malloc(strlen(DecodeUnicodeString(Files.ID_FullName))+1);
282 				sprintf(Entry->Name,"%s",DecodeUnicodeString(Files.ID_FullName));
283 				/* converting Gammu drives to phone drives */
284 				if (Entry->Name[0]=='a' || Entry->Name[0]=='A') {
285 					Entry->Name[0]='b';
286 				} else if (Entry->Name[0]=='d' || Entry->Name[0]=='D') {
287 					Entry->Name[0]='a';
288 				}
289 
290 				Entry->NameUP = malloc(strlen(DecodeUnicodeString(Files.ID_FullName))+1);
291 				for (i = 0; i < strlen(DecodeUnicodeString(Files.ID_FullName)) + 1; i++) {
292 					Entry->NameUP[i] = tolower(Entry->Name[i]);
293 				}
294 			}
295 		} else {
296 			Names = (unsigned char *)realloc(Names,NamesPos+UnicodeLength(Files.ID_FullName)*2+2);
297 			CopyUnicodeString(Names+NamesPos,Files.ID_FullName);
298 			NamesPos+=UnicodeLength(Files.ID_FullName)*2+2;
299 
300 			Names2 = (unsigned char *)realloc(Names2,NamesPos2+UnicodeLength(Files.Name)*2+2);
301 			CopyUnicodeString(Names2+NamesPos2,Files.Name);
302 			NamesPos2+=UnicodeLength(Files.Name)*2+2;
303 		}
304 
305 		Start = FALSE;
306 	}
307 	if (First != NULL) {
308 		/* sorting songs names */
309 		Entry = First;
310 		while (Entry->Next != NULL) {
311 			if (strcmp(Entry->NameUP,Entry->Next->NameUP)>0) {
312 				Pointer=Entry->Next->Name;
313 				Entry->Next->Name = Entry->Name;
314 				Entry->Name = Pointer;
315 
316 				Pointer=Entry->Next->NameUP;
317 				Entry->Next->NameUP = Entry->NameUP;
318 				Entry->NameUP = Pointer;
319 
320 				Entry = First;
321 				continue;
322 			}
323 			Entry = Entry->Next;
324 		}
325 		/* we checking, if file already exist.if yes, we look for another... */
326 		i 		= 0;
327 		Files3.Buffer 	= NULL;
328 		while (1) {
329 			CopyUnicodeString(Files3.ID_FullName,IDFolder);
330 	        	CopyUnicodeString(Buffer2,Name);
331 			if (i!=0) {
332 				sprintf(Buffer, "%ld", (long)i);
333 		        	EncodeUnicode(Buffer2+UnicodeLength(Buffer2)*2,Buffer,strlen(Buffer));
334 			}
335 	        	EncodeUnicode(Buffer2+UnicodeLength(Buffer2)*2,".m3u",4);
336 
337 			Start = TRUE;
338 			Available = FALSE;
339 			while (1) {
340 				error = GSM_GetFolderListing(gsm,&Files3,Start);
341 				if (error == ERR_FOLDERPART) {
342 					printf("%s\n", _("  Problem with adding playlist"));
343 					break;
344 				}
345 				if (error == ERR_EMPTY) break;
346 			    	Print_Error(error);
347 
348 				if (!Files3.Folder) {
349 					if (mywstrncasecmp(Buffer2,Files3.Name,-1)) {
350 						Available = TRUE;
351 						break;
352 					}
353 				}
354 				Start = FALSE;
355 			}
356 			if (!Available) break;
357 			i++;
358 		}
359 
360 		/* preparing new playlist file date */
361 		Files2.System	 = FALSE;
362 		Files2.Folder 	 = FALSE;
363 		Files2.ReadOnly	 = FALSE;
364 		Files2.Hidden	 = FALSE;
365 		Files2.Protected = FALSE;
366 		Files2.ModifiedEmpty = FALSE;
367 		GSM_GetCurrentDateTime (&Files2.Modified);
368 		CopyUnicodeString(Files2.ID_FullName,IDFolder);
369 	        CopyUnicodeString(Files2.Name,Buffer2);
370 
371 		/* preparing new playlist file content */
372 		Files2.Buffer=NULL;
373 		Files2.Buffer = (unsigned char *)realloc(Files2.Buffer,10);
374 		sprintf(Files2.Buffer,"#EXTM3U%c%c",13,10);
375 		Files2.Used = 9;
376 		Entry = First;
377 		while (Entry != NULL) {
378 			Files2.Buffer = (unsigned char *)realloc(Files2.Buffer, Files2.Used+strlen(Entry->Name) + 2 + 1);
379 			sprintf(Files2.Buffer + Files2.Used, "%s%c%c", Entry->Name, 13, 10);
380 			Files2.Used += strlen(Entry->Name) + 2;
381 			Entry = Entry->Next;
382 		}
383 		Files2.Used	 -= 2;
384 		for (i=0;i<Files2.Used;i++) {
385 			if (Files2.Buffer[i]=='/') Files2.Buffer[i]='\\';
386 		}
387 
388 		/* adding new playlist file */
389 		sprintf(Buffer2, _("Writing file %s:"), DecodeUnicodeString(Files2.Name));
390 		AddOneFile(&Files2, Buffer2, FALSE);
391 
392 		/* cleaning buffers */
393 		free(Files2.Buffer);
394 		Files2.Buffer = NULL;
395 
396 		Entry = First;
397 		while (Entry != NULL) {
398 			Prev = Entry;
399 			Entry = Entry->Next;
400 			free(Prev->Name);
401 			free(Prev->NameUP);
402 			free(Prev);
403 		}
404 	}
405 
406 	/* going into subfolders */
407 	if (NamesPos != 0) {
408 		i = 0; j = 0;
409 		while (i != NamesPos) {
410 			NokiaAddPlayLists2(Names+i,Names2+j,IDFolder);
411 			i+=UnicodeLength(Names+i)*2+2;
412 			j+=UnicodeLength(Names2+j)*2+2;
413 		}
414 	}
415 
416 out:
417 	free(Names);
418 	free(Names2);
419 	if (First != NULL) {
420 		free(First);
421 	}
422 }
423 
NokiaAddPlayLists(int argc UNUSED,char * argv[]UNUSED)424 void NokiaAddPlayLists(int argc UNUSED, char *argv[] UNUSED)
425 {
426 	GSM_Error error;
427 	gboolean 			Start = TRUE;
428 	GSM_File	 	Files;
429 	unsigned char		buffer[20],buffer2[20],IDFolder[100];
430 
431 	GSM_Init(TRUE);
432 
433 	/* delete old playlists */
434 	EncodeUnicode(IDFolder,"d:\\predefplaylist",17);
435 	CopyUnicodeString(Files.ID_FullName,IDFolder);
436 	error = GSM_GetFolderListing(gsm,&Files,Start);
437 	if (error == ERR_FILENOTEXIST) {
438 		EncodeUnicode(IDFolder,"d:\\predefgallery\\predefplaylist",17+14);
439 		CopyUnicodeString(Files.ID_FullName,IDFolder);
440 		error = GSM_GetFolderListing(gsm,&Files,Start);
441 	} else if (error != ERR_EMPTY) {
442 	    	Print_Error(error);
443 	}
444 	if (error == ERR_FILENOTEXIST) {
445 		printf("%s\n", _("Your phone model is not supported. Please report it to authors (see <https://wammu.eu/support/bugs/>). Thank you."));
446 		GSM_Terminate();
447 		Terminate(2);
448 	} else if (error != ERR_EMPTY) {
449 	    	Print_Error(error);
450 	}
451 	while (1) {
452 		if (!Files.Folder) {
453 			if (strstr(DecodeUnicodeConsole(Files.Name),".m3u")!=NULL) {
454 				error = GSM_DeleteFile(gsm,Files.ID_FullName);
455 			    	Print_Error(error);
456 			}
457 		}
458 		Start = FALSE;
459 		error = GSM_GetFolderListing(gsm,&Files,Start);
460 		if (error == ERR_FOLDERPART) {
461 			printf("%s\n", _("Problem with deleting playlist"));
462 			break;
463 		}
464 		if (error == ERR_EMPTY) break;
465 	    	Print_Error(error);
466 	}
467 
468 	/* go over phone memory and add new one playlists */
469 	EncodeUnicode(buffer,"d:",2);
470 	EncodeUnicode(buffer2,"root",4);
471 	NokiaAddPlayLists2(buffer,buffer2,IDFolder);
472 	/* go over memory card and add new one playlists */
473 	EncodeUnicode(buffer,"a:",2);
474 	EncodeUnicode(buffer2,"root",4);
475 	NokiaAddPlayLists2(buffer,buffer2,IDFolder);
476 
477 	GSM_Terminate();
478 }
479 
480 struct NokiaFolderInfo {
481 	const char	*model;
482 	const char 	*parameter;
483 	const char	*folder;
484 	const char 	*level;
485 };
486 
487 struct NokiaFolderInfo Folder[] = {
488 	/* Language indepedent in DCT4 in filesystem 1 */
489 	{"",	 "Application",	   "applications",	"3"},
490 	{"",	 "Game",	   "games",		"3"},
491 	/* Language indepedent in DCT4/TIKU/BB5 in filesystem 2 */
492 	{"", 	 "Gallery",	   "d:/predefgallery/predefgraphics",			""},
493 	{"", 	 "Gallery2",	   "d:/predefgallery/predefgraphics/predefcliparts",	""},
494 	{"", 	 "Camera",	   "d:/predefgallery/predefphotos",			""},
495 	{"", 	 "Tones",	   "d:/predefgallery/predeftones",			""},
496 	{"", 	 "Tones2",	   "d:/predefgallery/predefmusic",			""},
497 	{"", 	 "Records",	   "d:/predefgallery/predefrecordings",			""},
498 	{"", 	 "Video",	   "d:/predefgallery/predefvideos",			""},
499 	{"", 	 "Playlist",	   "d:/predefplaylist",					""},
500 	{"", 	 "MemoryCard",	   "a:",						""},
501 	    /* now values first seen in S40 3.0 */
502 	{"",	 "Application",	   "d:/predefjava/predefcollections",			""},
503 	{"",	 "Game",	   "d:/predefjava/predefgames",				""},
504 
505 	/* Language depedent in DCT4 filesystem 1 */
506 	{"",	 "Gallery",	   "Clip-arts",					"3"},
507 	{"",	 "Gallery",	   "004F006200720061007A006B0069",		"3"},/* obrazki PL 6220 */
508 	{"",	 "Gallery",	   "Pictures",					"2"},/* 3510 */
509 	{"",	 "Gallery2",	   "Graphics",					"3"},
510 	{"",	 "Gallery2",	   "00470072006100660069006B0061",		"3"},/* grafika PL 6220 */
511 	{"",	 "Camera",	   "Images",					"3"},
512 	{"",	 "Camera",	   "005A0064006A0119006300690061",		"3"},/* zdjecia PL 6220 */
513 	{"",	 "Tones",	   "Tones",					"3"},
514 	{"",	 "Tones",	   "0044017A007700690119006B0069",		"3"},/* dzwieki pl 6220 */
515 	{"",	 "Records",	   "Recordings",				"3"},
516 	{"",	 "Records",	   "004E0061006700720061006E00690061",		"3"},/* nagrania pl 6220 */
517 	{"",	 "Video",	   "Video clips",				"3"},
518 	{"",	 "Video",	   "0057006900640065006F006B006C006900700079",	"3"},/* wideoklipy pl 6220 */
519 
520 	/* Language indepedent in OBEX */
521 	{"obex", "MMSUnreadInbox", "predefMessages\\predefINBOX", 		""},
522 	{"obex", "MMSReadInbox",   "predefMessages\\predefINBOX", 		""},
523 	{"obex", "MMSOutbox",	   "predefMessages\\predefOUTBOX", 		""},
524 	{"obex", "MMSSent",	   "predefMessages\\predefSENT", 		""},
525 	{"obex", "MMSDrafts",	   "predefMessages\\predefDRAFTS", 		""},
526 /* 	{"obex", "Application,	   "predefjava\\predefapplications", 		""}, */
527 /* 	{"obex", "Game",	   "predefjava\\predefgames", 			""}, */
528 	{"obex", "Gallery",	   "predefgallery\\predefgraphics", 		""},
529 	{"obex", "Tones",	   "predefgallery\\predeftones", 		""},
530 
531 	/* End of list */
532 	{"",	 "",		   "",		""}
533 };
534 
NokiaAddFile(int argc,char * argv[])535 void NokiaAddFile(int argc, char *argv[])
536 {
537 	GSM_Error error;
538 	GSM_File		File, Files, File2;
539 	FILE			*file;
540 	unsigned char 		buffer[10000],JAR[500],Vendor[500],Name[500],Version[500],FileID[400];
541 	gboolean 			Start = TRUE, Found = FALSE, wasclr;
542 	gboolean			ModEmpty = FALSE, Overwrite = FALSE, OverwriteAll = FALSE;
543 	size_t i = 0, Pos;
544 	int Size, Size2;
545 	int nextlong, j;
546 
547 	buffer[0] = 0;
548 
549 	while (Folder[i].parameter[0] != 0) {
550 		if (strcasecmp(argv[2],Folder[i].parameter) == 0) {
551 			Found = TRUE;
552 			break;
553 		}
554 		i++;
555 	}
556 	if (!Found) {
557 		printf(_("What folder type (\"%s\") ?\n"),argv[2]);
558 		Terminate(2);
559 	}
560 
561 	if (strcasecmp(argv[2],"Application") == 0 || strcasecmp(argv[2],"Game") == 0) {
562 		sprintf(buffer, "%s.jad", argv[3]);
563 		file = fopen(buffer, "rb");
564 		if (file == NULL) {
565 			printf_err(_("Can not open file %s\n"), buffer);
566 			Print_Error(ERR_CANTOPENFILE);
567 		}
568 		fclose(file);
569 		sprintf(buffer, "%s.jar", argv[3]);
570 		file = fopen(buffer, "rb");
571 		if (file == NULL) {
572 			printf_err(_("Can not open file %s\n"), buffer);
573 			Print_Error(ERR_CANTOPENFILE);
574 		}
575 		fclose(file);
576 	} else {
577 		file = fopen(argv[3],"rb");
578 		if (file == NULL) {
579 			printf_err(_("Can not open file %s\n"), argv[3]);
580 			Print_Error(ERR_CANTOPENFILE);
581 		}
582 		fclose(file);
583 	}
584 
585 	GSM_Init(TRUE);
586 
587 	Found = FALSE;
588     	if (GSM_GetUsedConnection(gsm) == GCT_IRDAOBEX || GSM_GetUsedConnection(gsm) == GCT_BLUEOBEX) {
589 		i = 0;
590 		while (Folder[i].parameter[0] != 0) {
591 			if (!strcmp("obex",Folder[i].model) &&
592 			     strcasecmp(argv[2],Folder[i].parameter) == 0) {
593 				EncodeUnicode(Files.ID_FullName,Folder[i].folder,strlen(Folder[i].folder));
594 				Found = TRUE;
595 				break;
596 			}
597 			i++;
598 		}
599 		if (!Found) {
600 			printf("%s\n", _("Folder not found. Probably function not supported!"));
601 			GSM_Terminate();
602 			Terminate(2);
603 		}
604 	} else if (GSM_IsPhoneFeatureAvailable(GSM_GetModelInfo(gsm), F_FILES2)) {
605 		i = 0;
606 		while (Folder[i].parameter[0] != 0) {
607 			if ((Folder[i].folder[0] == 'a' || Folder[i].folder[0] == 'd') &&
608 			    Folder[i].level[0] == 0x00 &&
609 			    strcasecmp(argv[2],Folder[i].parameter) == 0) {
610 				if (strstr(Folder[i].folder,"d:/predefjava/")!= NULL &&
611 				    !GSM_IsPhoneFeatureAvailable(GSM_GetModelInfo(gsm), F_SERIES40_30)) {
612 					i++;
613 					continue;
614 				}
615 				EncodeUnicode(Files.ID_FullName,Folder[i].folder,strlen(Folder[i].folder));
616 				Found = TRUE;
617 				break;
618 			}
619 			i++;
620 		}
621 	}
622 	if (!Found) {
623 		fprintf(stderr, "%s", _("Searching for phone folder: "));
624 		while (1) {
625 			error = GSM_GetNextFileFolder(gsm,&Files,Start);
626 			if (error == ERR_EMPTY) break;
627 		    	Print_Error(error);
628 
629 			if (Files.Folder) {
630 				smprintf(gsm, "folder %s level %i\n",DecodeUnicodeConsole(Files.Name),Files.Level);
631 				Found 	= FALSE;
632 				i 	= 0;
633 				while (Folder[i].parameter[0] != 0) {
634 					EncodeUnicode(buffer,Folder[i].folder,strlen(Folder[i].folder));
635 					smprintf(gsm, "comparing \"%s\" \"%s\" \"%s\"\n",GSM_GetModelInfo(gsm)->model,DecodeUnicodeString(Files.ID_FullName),Folder[i].level);
636 					if (strcasecmp(argv[2],Folder[i].parameter) == 0  &&
637 					    mywstrncasecmp(Files.Name,buffer,0) &&
638 					    Files.Level == atoi(Folder[i].level)) {
639 						smprintf(gsm, "found 1\n");
640 						Found = TRUE;
641 						break;
642 					}
643 					if (strcasecmp(argv[2],Folder[i].parameter) == 0 &&
644 					    !strcmp(DecodeUnicodeString(Files.ID_FullName),Folder[i].folder) &&
645 					    Folder[i].level[0] == 0x00) {
646 						Found = TRUE;
647 						smprintf(gsm, "found 2\n");
648 						break;
649 					}
650 					if (Folder[i].folder[0]>='0'&&Folder[i].folder[0] <='9') {
651 						DecodeHexUnicode (buffer, Folder[i].folder,strlen(Folder[i].folder));
652 						smprintf(gsm, "comparing \"%s\"",DecodeUnicodeString(buffer));
653 						smprintf(gsm, "and \"%s\"\n",DecodeUnicodeString(Files.Name));
654 						if (strcasecmp(argv[2],Folder[i].parameter) == 0  &&
655 						    mywstrncasecmp(Files.Name,buffer,0) &&
656 						    Files.Level == atoi(Folder[i].level)) {
657 							Found = TRUE;
658 							smprintf(gsm, "found 3\n");
659 							break;
660 						}
661 					}
662 					i++;
663 				}
664 				if (Found) break;
665 			}
666 			fprintf(stderr, "*");
667 
668 			Start = FALSE;
669 		}
670 		fprintf(stderr, "\n");
671 		fflush(stderr);
672 	}
673 	if (!Found) {
674 		printf("%s\n", _("Folder not found. Probably function not supported!"));
675 		GSM_Terminate();
676 		Terminate(2);
677 	}
678 	File.Buffer 	= NULL;
679 	File.Protected  = FALSE;
680 	File.ReadOnly   = FALSE;
681 	File.Hidden	= FALSE;
682 	File.System	= FALSE;
683 
684 	if (strcasecmp(argv[2],"Application") == 0 || strcasecmp(argv[2],"Game") == 0) {
685 		/* reading jar file */
686 		sprintf(buffer,"%s.jar",argv[3]);
687 		error = GSM_ReadFile(buffer, &File);
688 		Print_Error(error);
689 		Size2 = File.Used;
690 
691 		/* reading jad file */
692 		sprintf(buffer,"%s.jad",argv[3]);
693 		error = GSM_ReadFile(buffer, &File);
694 		Print_Error(error);
695 
696 		/* Getting values from JAD file */
697 		error = GSM_JADFindData(&File, Vendor, Name, JAR, Version, &Size);
698 		if (error == ERR_FILENOTSUPPORTED) {
699 			if (Vendor[0] == 0x00) {
700 				fprintf(stderr, "%s\n", _("No vendor info in JAD file!"));
701 				GSM_Terminate();
702 				return;
703 			}
704 			if (Name[0] == 0x00) {
705 				fprintf(stderr, "%s\n", _("No name info in JAD file!"));
706 				GSM_Terminate();
707 				return;
708 			}
709 			if (JAR[0] == 0x00) {
710 				fprintf(stderr, "%s\n", _("No JAR URL info in JAD file!"));
711 				GSM_Terminate();
712 				return;
713 			}
714 		}
715 		if (Size != Size2) {
716 			printf_info("%s\n", _("Declared JAR file size is different than real. Fixed by Gammu."));
717 			for (i=0;i<File.Used;i++) {
718 				if (strncasecmp(File.Buffer+i,"MIDlet-Jar-Size: ",17) == 0) {
719 					break;
720 				}
721 			}
722 			Pos = i;
723 			while (TRUE) {
724 				if (Pos ==0 || File.Buffer[Pos] == 13 || File.Buffer[Pos] == 10) break;
725 				Pos--;
726 			}
727 			i+= 15;
728 			while (TRUE) {
729 				if (i == File.Used || File.Buffer[i] == 13 || File.Buffer[i] == 10) break;
730 				i++;
731 			}
732 			while (i != File.Used) {
733 				File.Buffer[Pos] = File.Buffer[i];
734 				i++;
735 				Pos++;
736 			}
737 			File.Used = File.Used - (i - Pos);
738 			File.Buffer = realloc(File.Buffer,File.Used);
739 		} else if (Size == -1) {
740 			printf_info("%s\n", _("No JAR size info in JAD file. Added by Gammu."));
741 		}
742 		if (Size != Size2) {
743 			sprintf(buffer,"\nMIDlet-Jar-Size: %i",Size2);
744 			File.Buffer = realloc(File.Buffer,File.Used + strlen(buffer));
745 			memcpy(File.Buffer+File.Used,buffer,strlen(buffer));
746 			File.Used += strlen(buffer);
747 			Size = Size2;
748 		}
749   		fprintf(stderr, _("Adding \"%s\""),Name);
750 		if (Version[0] != 0x00) fprintf(stderr, _(" version %s"),Version);
751 		fprintf(stderr, _(" created by %s\n"),Vendor);
752 
753 		/* Bostjan Muller 3200 RH-30 3.08 */
754 		if (strstr(JAR,"http://") != NULL) {
755 			i = strlen(JAR)-1;
756 			while (JAR[i] != '/') i--;
757 			strcpy(buffer,JAR+i+1);
758 			strcpy(JAR,buffer);
759 			smprintf(gsm, "New file name is \"%s\"\n",JAR);
760 		}
761 
762 		/* Changing all #13 or #10 to #13#10 in JAD */
763 		Pos    = 0;
764 		wasclr = FALSE;
765 		for (i=0;i<File.Used;i++) {
766 			switch (File.Buffer[i]) {
767 			case 0x0D:
768 			case 0x0A:
769 				if (!wasclr) {
770 					buffer[Pos++] = 0x0D;
771 					buffer[Pos++] = 0x0A;
772 					wasclr = TRUE;
773 				} else wasclr = FALSE;
774 				break;
775 			default:
776 				buffer[Pos++] 	= File.Buffer[i];
777 				wasclr		= FALSE;
778 			}
779 		}
780 		File.Buffer = realloc(File.Buffer, Pos);
781 		File.Used   = Pos;
782 		memcpy(File.Buffer,buffer,Pos);
783 
784 		if (argc > 4) {
785 			for (j = 4; j < argc; j++) {
786 				if (strcasecmp(argv[j],"-overwrite") == 0) Overwrite = TRUE;
787 				if (strcasecmp(argv[j],"-overwriteall") == 0) {
788 					Overwrite = TRUE;
789 					OverwriteAll = TRUE;
790 				}
791 			}
792 		}
793 
794 		/* adding folder */
795 		if (strstr(DecodeUnicodeString(Files.ID_FullName),"d:/predefjava/")== NULL) {
796 			strcpy(buffer,Vendor);
797 			strcat(buffer,Name);
798 			EncodeUnicode(File.Name,buffer,strlen(buffer));
799 			CopyUnicodeString(File.ID_FullName,Files.ID_FullName);
800 			error = GSM_AddFolder(gsm,&File);
801 			if (Overwrite && (error == ERR_FILEALREADYEXIST)) {
802 				printf_info("%s\n", _("Application already exists. Deleting by Gammu."));
803 
804 				Start = TRUE;
805 				CopyUnicodeString(File2.ID_FullName,Files.ID_FullName);
806 				while (1) {
807 					error = GSM_GetFolderListing(gsm,&File2,Start);
808 					if (error == ERR_EMPTY) break;
809 					Print_Error(error);
810 
811 					if (File2.Folder && !strcmp(DecodeUnicodeString(File2.Name),buffer)) {
812 						break;
813 					}
814 
815 					Start = FALSE;
816 				}
817 
818 				Start = TRUE;
819 				CopyUnicodeString(File.ID_FullName,File2.ID_FullName);
820 				while (1) {
821 					error = GSM_GetFolderListing(gsm,&File2,Start);
822 					if (error == ERR_EMPTY) break;
823 					Print_Error(error);
824 
825 					strcpy(buffer,DecodeUnicodeString(File2.Name));
826 
827 					i = strlen(buffer);
828 					if (i < 4) continue;
829 
830 					i -= 4;
831 
832 					if (OverwriteAll ||
833 					    strcmp(buffer + i,".jad") == 0 ||
834 					    strcmp(buffer + i,".jar") == 0) {
835 						fprintf(stderr, _("  Deleting %s\n"),buffer);
836 					error = GSM_DeleteFile(gsm,File2.ID_FullName);
837 					Print_Error(error);
838 
839 						CopyUnicodeString(File2.ID_FullName,File.ID_FullName);
840 						Start = TRUE;
841 					} else {
842 						Start = FALSE;
843 					}
844 				}
845 			} else {
846 			    	Print_Error(error);
847 			}
848 			CopyUnicodeString(FileID,File.ID_FullName);
849 		} else {
850 			if (Overwrite) {
851 				Start = TRUE;
852 				CopyUnicodeString(File2.ID_FullName,Files.ID_FullName);
853 
854 				printf_info("%s\n", _("Application already exists. Deleting by Gammu."));
855 
856 				while (TRUE) {
857 					error = GSM_GetFolderListing(gsm,&File2,Start);
858 					if (error == ERR_EMPTY) break;
859 					Print_Error(error);
860 
861 					strcpy(buffer,DecodeUnicodeString(File2.Name));
862 
863 					i = strlen(Name);
864 					if (strncmp(buffer,Name,i) == 0 &&
865 					    (strcmp(buffer + i,".jad") == 0 ||
866 					     strcmp(buffer + i,".jar") == 0 ||
867 					     (strncmp(buffer + i,"\177_m_",4) == 0 && OverwriteAll))) {
868 						fprintf(stderr, _("  Deleting %s\n"),buffer);
869 						error = GSM_DeleteFile(gsm,File2.ID_FullName);
870 						Print_Error(error);
871 
872 						CopyUnicodeString(File2.ID_FullName,Files.ID_FullName);
873 						Start = TRUE;
874 					} else {
875 						Start = FALSE;
876 					}
877 				}
878 			}
879 
880 			CopyUnicodeString(FileID,Files.ID_FullName);
881 			CopyUnicodeString(File.ID_FullName,Files.ID_FullName);
882 		}
883 
884 		/* adding jad file */
885 		strcpy(buffer,JAR);
886 		buffer[strlen(buffer) - 1] = 'd';
887 		EncodeUnicode(File.Name,buffer,strlen(buffer));
888 		File.Type 	   = GSM_File_Other;
889 		File.ModifiedEmpty = TRUE;
890 		smprintf(gsm, "file id is \"%s\"\n",DecodeUnicodeString(File.ID_FullName));
891 		AddOneFile(&File, _("Writing JAD file:"), FALSE);
892 
893 		if (argc > 4) {
894 			for (j = 4; j < argc; j++) {
895 				if (strcasecmp(argv[j],"-readonly") == 0) File.ReadOnly = TRUE;
896 			}
897 		}
898 
899 		/* reading jar file */
900 		sprintf(buffer,"%s.jar",argv[3]);
901 		error = GSM_ReadFile(buffer, &File);
902 		Print_Error(error);
903 
904 		/* adding jar file */
905 		CopyUnicodeString(File.ID_FullName,FileID);
906 		strcpy(buffer,JAR);
907 		EncodeUnicode(File.Name,buffer,strlen(buffer));
908 		File.Type 	   = GSM_File_Java_JAR;
909 		File.ModifiedEmpty = TRUE;
910 		AddOneFile(&File, _("Writing JAR file:"), FALSE);
911 		free(File.Buffer);
912 		GSM_Terminate();
913 		return;
914 	}
915 
916 	if (strcasecmp(argv[2],"Gallery" 	 ) == 0 ||
917 	    strcasecmp(argv[2],"Gallery2"	 ) == 0 ||
918 	    strcasecmp(argv[2],"Camera"  	 ) == 0 ||
919 	    strcasecmp(argv[2],"Tones"   	 ) == 0 ||
920 	    strcasecmp(argv[2],"Tones2"  	 ) == 0 ||
921 	    strcasecmp(argv[2],"Records" 	 ) == 0 ||
922 	    strcasecmp(argv[2],"Video"   	 ) == 0 ||
923 	    strcasecmp(argv[2],"Playlist"	 ) == 0 ||
924 	    strcasecmp(argv[2],"MemoryCard"   ) == 0) {
925 		strcpy(buffer,argv[3]);
926 		if (argc > 4) {
927 			nextlong = 0;
928 			for (j = 4; j < argc; j++) {
929 				switch(nextlong) {
930 				case 0:
931 					if (strcasecmp(argv[j],"-name") == 0) {
932 						nextlong = 1;
933 						continue;
934 					}
935 					if (strcasecmp(argv[j],"-protected") == 0) {
936 						File.Protected = TRUE;
937 						continue;
938 					}
939 					if (strcasecmp(argv[j],"-readonly") == 0) {
940 						File.ReadOnly = TRUE;
941 						continue;
942 					}
943 					if (strcasecmp(argv[j],"-hidden") == 0) {
944 						File.Hidden = TRUE;
945 						continue;
946 					}
947 					if (strcasecmp(argv[j],"-system") == 0) {
948 						File.System = TRUE;
949 						continue;
950 					}
951 					if (strcasecmp(argv[j],"-newtime") == 0) {
952 						ModEmpty = TRUE;
953 						continue;
954 					}
955 					printf(_("Parameter \"%s\" unknown\n"),argv[j]);
956 					Terminate(2);
957 				case 1:
958 					strcpy(buffer,argv[j]);
959 					nextlong = 0;
960 					break;
961 				}
962 			}
963 			if (nextlong!=0) {
964 				printf_err("%s\n", _("Parameter missing!"));
965 				Terminate(2);
966 			}
967 		}
968 	}
969 
970 	error = GSM_ReadFile(argv[3], &File);
971 	Print_Error(error);
972 	if (ModEmpty) File.ModifiedEmpty = TRUE;
973 
974 	CopyUnicodeString(File.ID_FullName,Files.ID_FullName);
975 	EncodeUnicode(File.Name,buffer,strlen(buffer));
976 	for (i=strlen(buffer)-1;i>0;i--) {
977 		if (buffer[i] == '\\' || buffer[i] == '/') break;
978 	}
979 	if (buffer[i] == '\\' || buffer[i] == '/') {
980 		EncodeUnicode(File.Name,buffer+i+1,strlen(buffer)-i-1);
981 	}
982 
983 	GSM_IdentifyFileFormat(&File);
984 
985 	AddOneFile(&File, _("Writing file:"), FALSE);
986 	free(File.Buffer);
987 	GSM_Terminate();
988 }
989 
NokiaGetADC(int argc,char * argv[])990 void NokiaGetADC(int argc, char *argv[])
991 {
992 	GSM_Init(TRUE);
993 
994 #ifdef GSM_ENABLE_NOKIA_DCT3
995 	if (CheckDCT3Only() != ERR_NOTSUPPORTED) {
996 		DCT3GetADC(argc,argv);
997 	}
998 #endif
999 #ifdef GSM_ENABLE_NOKIA_DCT4
1000 	if (CheckDCT4Only() != ERR_NOTSUPPORTED) {
1001 		DCT4GetADC(argc, argv);
1002 	}
1003 #endif
1004 
1005 	GSM_Terminate();
1006 }
1007 
NokiaDisplayTest(int argc,char * argv[])1008 void NokiaDisplayTest(int argc, char *argv[])
1009 {
1010 	GSM_Init(TRUE);
1011 
1012 #ifdef GSM_ENABLE_NOKIA_DCT3
1013 	if (CheckDCT3Only() != ERR_NOTSUPPORTED) {
1014 		DCT3DisplayTest(argc,argv);
1015 	}
1016 #endif
1017 #ifdef GSM_ENABLE_NOKIA_DCT4
1018 	if (CheckDCT4Only() != ERR_NOTSUPPORTED) {
1019 		DCT4DisplayTest(argc, argv);
1020 	}
1021 #endif
1022 
1023 	GSM_Terminate();
1024 }
1025 
NokiaGetT9(int argc,char * argv[])1026 void NokiaGetT9(int argc, char *argv[])
1027 {
1028 	GSM_Init(TRUE);
1029 
1030 #ifdef GSM_ENABLE_NOKIA_DCT3
1031 	if (CheckDCT3Only() != ERR_NOTSUPPORTED) {
1032 		DCT3GetT9(argc,argv);
1033 	}
1034 #endif
1035 #ifdef GSM_ENABLE_NOKIA_DCT4
1036 	if (CheckDCT4Only() != ERR_NOTSUPPORTED) {
1037 		DCT4GetT9(argc, argv);
1038 	}
1039 #endif
1040 
1041 	GSM_Terminate();
1042 }
1043 
NokiaVibraTest(int argc,char * argv[])1044 void NokiaVibraTest(int argc, char *argv[])
1045 {
1046 	GSM_Init(TRUE);
1047 
1048 #ifdef GSM_ENABLE_NOKIA_DCT3
1049 	if (CheckDCT3Only() != ERR_NOTSUPPORTED) {
1050 		DCT3VibraTest(argc,argv);
1051 	}
1052 #endif
1053 #ifdef GSM_ENABLE_NOKIA_DCT4
1054 	if (CheckDCT4Only() != ERR_NOTSUPPORTED) {
1055 		DCT4VibraTest(argc, argv);
1056 	}
1057 #endif
1058 
1059 	GSM_Terminate();
1060 }
1061 #endif
1062 
1063 /* How should editor hadle tabs in this file? Add editor commands here.
1064  * vim: noexpandtab sw=8 ts=8 sts=8:
1065  */
1066 
1067