+ switch ( GSM_ReadVCalendarFile(argv[0], &CalendarNote, &number) ) {
+ case GE_NONE:
+ break;
+ case GE_CANTOPENFILE:
+ fprintf(stdout, _("Failed to open vCalendar file \"%s\"\n"),argv[0]);
+ return -1;
+ case GE_TOOSHORT:
+ fprintf(stdout, _("Number of given calendar note is too high (max=%i)\n"),number);
+ return(-1);
+ default:
+ fprintf(stdout, _("Failed to parse vCalendar file \"%s\"\n"),argv[0]);
+ return -1;
+ }
+
+ fbusinit(NULL);
+
+ /* Error 22=Calendar full ;-) */
+
+ error=GSM->WriteCalendarNote(&CalendarNote);
+ switch (error) {
+ case GE_NONE:
+ fprintf(stdout, _("Succesfully written!\n"));break;
+ case GE_TOOLONG:
+ fprintf(stdout, _("Too long text in calendar note!\n"));break;
+ default:
+ fprintf(stdout, _("Failed to write calendar note!\n"));break;
+ }
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+/* Calendar note deleting. */
+
+int deletecalendarnote(char *Index)
+{
+
+ GSM_CalendarNote CalendarNote;
+
+ CalendarNote.Location=atoi(Index);
+
+ fbusinit(NULL);
+
+ if (GSM->DeleteCalendarNote(&CalendarNote) == GE_NONE) {
+ fprintf(stdout, _(" Calendar note deleted.\n"));
+ }
+ else {
+ fprintf(stderr, _("The calendar note can not be deleted\n"));
+
+ GSM->Terminate();
+ return -1;
+ }
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+/* Setting the date and time. */
+
+int setdatetime(int argc, char *argv[])
+{
+ struct tm *now;
+ time_t nowh;
+ GSM_DateTime Date;
+
+ fbusinit(NULL);
+
+ nowh=time(NULL);
+ now=localtime(&nowh);
+
+ Date.Year = now->tm_year;
+ Date.Month = now->tm_mon+1;
+ Date.Day = now->tm_mday;
+ Date.Hour = now->tm_hour;
+ Date.Minute = now->tm_min;
+ Date.Second = now->tm_sec;
+
+ if (argc>0) Date.Year = atoi (argv[0]);
+ if (argc>1) Date.Month = atoi (argv[1]);
+ if (argc>2) Date.Day = atoi (argv[2]);
+ if (argc>3) Date.Hour = atoi (argv[3]);
+ if (argc>4) Date.Minute = atoi (argv[4]);
+
+ if (Date.Year<1900)
+ {
+
+ /* Well, this thing is copyrighted in U.S. This technique is known as
+ Windowing and you can read something about it in LinuxWeekly News:
+ http://lwn.net/1999/features/Windowing.phtml. This thing is beeing
+ written in Czech republic and Poland where algorithms are not allowed
+ to be patented. */
+
+ if (Date.Year>90)
+ Date.Year = Date.Year+1900;
+ else
+ Date.Year = Date.Year+2000;
+ }
+
+ /* FIXME: Error checking should be here. */
+ GSM->SetDateTime(&Date);
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+/* In this mode we receive the date and time from mobile phone. */
+
+int getdatetime(void) {
+
+ GSM_DateTime date_time;
+
+ fbusinit(NULL);
+
+ if (GSM->GetDateTime(&date_time)==GE_NONE) {
+ if (date_time.IsSet) {
+ fprintf(stdout, _("Date: %s %4d/%02d/%02d\n"),
+ DayOfWeek(date_time.Year, date_time.Month, date_time.Day),
+ date_time.Year, date_time.Month, date_time.Day);
+ fprintf(stdout, _("Time: %02d:%02d:%02d\n"), date_time.Hour, date_time.Minute, date_time.Second);
+ } else {
+ fprintf(stdout, _("Date and time not set in phone\n"));
+ }
+ } else {
+ fprintf(stdout,_("Error!\n"));
+ }
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+/* Setting the alarm. */
+
+int setalarm(char *argv[])
+{
+
+ GSM_DateTime Date;
+
+ fbusinit(NULL);
+
+ Date.Hour = atoi(argv[0]);
+ Date.Minute = atoi(argv[1]);
+
+ GSM->SetAlarm(1, &Date);
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+/* Getting the alarm. */
+
+int getalarm(void) {
+
+ GSM_DateTime date_time;
+
+ fbusinit(NULL);
+
+ if (GSM->GetAlarm(0, &date_time)==GE_NONE) {
+ fprintf(stdout, _("Alarm: %s\n"), (date_time.IsSet)?"on":"off");
+ fprintf(stdout, _("Time: %02d:%02d\n"), date_time.Hour, date_time.Minute);
+ } else {
+ fprintf(stdout,_("Error!\n"));
+ }
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+/* In monitor mode we don't do much, we just initialise the fbus code.
+ Note that the fbus code no longer has an internal monitor mode switch,
+ instead compile with DEBUG enabled to get all the gumpf. */
+
+int monitormode(int argc, char *argv[])
+{
+
+ float rflevel=-1, batterylevel=-1;
+ unsigned char loop=1;
+
+ GSM_PowerSource powersource=-1;
+ GSM_RFUnits rf_units = GRF_Arbitrary;
+ GSM_BatteryUnits batt_units = GBU_Arbitrary;
+
+ GSM_NetworkInfo NetworkInfo;
+ GSM_CBMessage CBMessage;
+
+ GSM_MemoryStatus SIMMemoryStatus = {GMT_SM, 0, 0};
+ GSM_MemoryStatus PhoneMemoryStatus = {GMT_ME, 0, 0};
+ GSM_MemoryStatus DC_MemoryStatus = {GMT_DC, 0, 0};
+ GSM_MemoryStatus EN_MemoryStatus = {GMT_EN, 0, 0};
+ GSM_MemoryStatus FD_MemoryStatus = {GMT_FD, 0, 0};
+ GSM_MemoryStatus LD_MemoryStatus = {GMT_LD, 0, 0};
+ GSM_MemoryStatus MC_MemoryStatus = {GMT_MC, 0, 0};
+ GSM_MemoryStatus ON_MemoryStatus = {GMT_ON, 0, 0};
+ GSM_MemoryStatus RC_MemoryStatus = {GMT_RC, 0, 0};
+
+ GSM_SMSStatus SMSStatus = {0, 0};
+
+ char Number[20];
+
+ /* evaluate for presence of "-noloop" argument in parameter */
+ if(argc>0)
+ {
+ if( strcmp(argv[0],"-noloop" ) && strcmp(argv[0],"-nl" ))
+ {
+ usage();
+ return -1;
+ }
+ else
+ loop=0;
+ }
+
+ /* We do not want to monitor serial line forever - press Ctrl+C to stop the
+ monitoring mode. */
+
+ signal(SIGINT, interrupted);
+
+ fprintf (stderr, _("Entering monitor mode...\n"));
+ fprintf (stderr, _("Initialising GSM interface...\n"));
+
+ /* Initialise the code for the GSM interface. */
+
+ fbusinit(NULL);
+
+ sleep(1);
+ GSM->EnableCellBroadcast();
+
+ /* Loop here indefinitely - allows you to see messages from GSM code in
+ response to unknown messages etc. The loops ends after pressing the
+ Ctrl+C. */
+ while (!bshutdown) {
+ if (GSM->GetRFLevel(&rf_units, &rflevel) == GE_NONE)
+ fprintf(stdout, _("RFLevel: %d\n"), (int)rflevel);
+
+ if (GSM->GetBatteryLevel(&batt_units, &batterylevel) == GE_NONE)
+ fprintf(stdout, _("Battery: %d\n"), (int)batterylevel);
+
+ if (GSM->GetPowerSource(&powersource) == GE_NONE)
+ fprintf(stdout, _("Power Source: %s\n"), (powersource==GPS_ACDC)?_("AC/DC"):_("battery"));
+
+ if (GSM->GetMemoryStatus(&SIMMemoryStatus) == GE_NONE)
+ fprintf(stdout, _("SIM: Used %d, Free %d\n"), SIMMemoryStatus.Used, SIMMemoryStatus.Free);
+
+ if (GSM->GetMemoryStatus(&PhoneMemoryStatus) == GE_NONE)
+ fprintf(stdout, _("Phone: Used %d, Free %d\n"), PhoneMemoryStatus.Used, PhoneMemoryStatus.Free);
+
+ if (GSM->GetMemoryStatus(&DC_MemoryStatus) == GE_NONE)
+ fprintf(stdout, _("DC: Used %d, Free %d\n"), DC_MemoryStatus.Used, DC_MemoryStatus.Free);
+
+ if (GSM->GetMemoryStatus(&EN_MemoryStatus) == GE_NONE)
+ fprintf(stdout, _("EN: Used %d, Free %d\n"), EN_MemoryStatus.Used, EN_MemoryStatus.Free);
+
+ if (GSM->GetMemoryStatus(&FD_MemoryStatus) == GE_NONE)
+ fprintf(stdout, _("FD: Used %d, Free %d\n"), FD_MemoryStatus.Used, FD_MemoryStatus.Free);
+
+ if (GSM->GetMemoryStatus(&LD_MemoryStatus) == GE_NONE)
+ fprintf(stdout, _("LD: Used %d, Free %d\n"), LD_MemoryStatus.Used, LD_MemoryStatus.Free);
+
+ if (GSM->GetMemoryStatus(&MC_MemoryStatus) == GE_NONE)
+ fprintf(stdout, _("MC: Used %d, Free %d\n"), MC_MemoryStatus.Used, MC_MemoryStatus.Free);
+
+ if (GSM->GetMemoryStatus(&ON_MemoryStatus) == GE_NONE)
+ fprintf(stdout, _("ON: Used %d, Free %d\n"), ON_MemoryStatus.Used, ON_MemoryStatus.Free);
+
+ if (GSM->GetMemoryStatus(&RC_MemoryStatus) == GE_NONE)
+ fprintf(stdout, _("RC: Used %d, Free %d\n"), RC_MemoryStatus.Used, RC_MemoryStatus.Free);
+
+ if (GSM->GetSMSStatus(&SMSStatus) == GE_NONE)
+ fprintf(stdout, _("SMS Messages: UnRead %d, Number %d\n"), SMSStatus.UnRead, SMSStatus.Number);
+
+ if (GSM->GetIncomingCallNr(Number) == GE_NONE)
+ fprintf(stdout, _("Incoming call: %s\n"), Number);
+
+ if (GSM->GetNetworkInfo(&NetworkInfo) == GE_NONE)
+ fprintf(stdout, _("Network: %s (%s), LAC: %s, CellID: %s\n"), GSM_GetNetworkName (NetworkInfo.NetworkCode), GSM_GetCountryName(NetworkInfo.NetworkCode), NetworkInfo.LAC, NetworkInfo.CellID);
+
+ if (GSM->ReadCellBroadcast(&CBMessage) == GE_NONE)
+ fprintf(stdout, _("Cell broadcast received on channel %d: %s\n"), CBMessage.Channel, CBMessage.Message);
+
+ if( !loop ) break;
+
+ sleep(1);
+ }
+
+ if( loop ) fprintf (stderr, _("Leaving monitor mode...\n"));
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+/* Shows texts from phone's display */
+
+int displayoutput()
+{
+
+ GSM_Error error;
+
+ fbusinit(NULL);
+
+ error=GSM->EnableDisplayOutput();
+
+ if (error == GE_NONE)
+ {
+
+ /* We do not want to see texts forever - press Ctrl+C to stop. */
+
+ signal(SIGINT, interrupted);
+
+ fprintf (stderr, _("Entering display monitoring mode...\n"));
+
+ /* Loop here indefinitely - allows you to read texts from phone's
+ display. The loops ends after pressing the Ctrl+C. */
+
+ while (!bshutdown)
+ sleep(1);
+
+ fprintf (stderr, _("Leaving display monitor mode...\n"));
+
+ error=GSM->DisableDisplayOutput();
+ if (error!=GE_NONE)
+ fprintf (stderr, _("Error!\n"));
+ } else
+ fprintf (stderr, _("Error!\n"));
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+/* Displays names of available ringtones */
+int allringtones()
+{
+ char model[64], rev[64];
+ int i;
+
+ fbusinit(NULL);
+
+ while (GSM->GetRevision(rev) != GE_NONE)
+ sleep(1);
+
+ while (GSM->GetModel(model) != GE_NONE)
+ sleep(1);
+
+ strncpy(rev,rev+2,5);
+ rev[5]=0;
+ PrepareRingingTones(model,rev);
+
+ for (i=1;i<=NumberOfRingtones();i++)
+ {
+ fprintf(stdout,_("%i. %s\n"),i,RingingToneName(0,i));
+ }
+
+ GSM->Terminate();
+
+ return 0;
+
+}
+
+/* Reads profile from phone and displays its' settings */
+
+int getprofile(int argc, char *argv[])
+{
+
+ int max_profiles;
+ int start, stop, i;
+ GSM_Profile profile;
+ GSM_Error error;
+
+ /* Hopefully is 64 larger as FB38_MAX* / FB61_MAX* */
+ char model[64], rev[64];
+
+ /* Initialise the code for the GSM interface. */
+
+ fbusinit(NULL);
+
+ profile.Number = 0;
+ error=GSM->GetProfile(&profile);
+
+ if (error == GE_NONE)
+ {
+
+ while (GSM->GetModel(model) != GE_NONE) sleep(1);
+
+ while (GSM->GetRevision(rev) != GE_NONE) sleep(1);
+
+ strncpy(rev,rev+2,5);
+ rev[5]=0;
+ PrepareRingingTones(model,rev);
+
+ switch(GetModelFeature (FN_PROFILES)) {
+ case F_PROF33:max_profiles=6;break;
+ case F_PROF51:max_profiles=3;break;
+ default :max_profiles=7;break;
+ }
+
+ if (argc>0)
+ {
+ profile.Number=atoi(argv[0])-1;
+ start=profile.Number;
+ stop=start+1;
+
+ if (profile.Number < 0)
+ {
+ fprintf(stderr, _("Profile number must be value from 1 to %d!\n"), max_profiles);
+ GSM->Terminate();
+ return -1;
+ }
+
+ if (profile.Number >= max_profiles)
+ {
+ fprintf(stderr, _("This phone supports only %d profiles!\n"), max_profiles);
+ GSM->Terminate();
+ return -1;
+ }
+ } else {
+ start=0;
+ stop=max_profiles;
+ }
+
+ i=start;
+ while (i<stop)
+ {
+ profile.Number=i;
+
+ if (profile.Number!=0) GSM->GetProfile(&profile);
+
+ printf("%d. \"%s\"", (profile.Number+1), profile.Name);
+ if (profile.DefaultName==-1) printf(" (name defined)");
+ printf("\n");
+
+#ifdef DEBUG
+ printf("Incoming call alert: %d\n", profile.CallAlert);
+ printf("Ringtone ID: %d\n", profile.Ringtone);
+ printf("Ringing volume: %d\n", profile.Volume);
+ printf("Message alert tone: %d\n", profile.MessageTone);
+ printf("Keypad tones: %d\n", profile.KeypadTone);
+ printf("Warning and game tones: %d\n", profile.WarningTone);
+ printf("Lights: %d\n", profile.Lights);
+ printf("Vibration: %d\n", profile.Vibration);
+ printf("Caller groups: 0x%02x\n", profile.CallerGroups);
+ printf("Automatic answer: %d\n", profile.AutomaticAnswer);
+ printf("Screen saver: %d\n", profile.ScreenSaver);
+ printf("\n");
+#endif
+
+ printf("Incoming call alert: %s\n", GetProfileCallAlertString(profile.CallAlert));
+
+ /* For different phones different ringtones names */
+ if (strcmp(RingingToneName(profile.Ringtone,0),""))
+ printf(_("Ringing tone: %s (number %d in phone menu)\n"),
+ RingingToneName(profile.Ringtone,0), RingingToneMenu(profile.Ringtone));
+ else
+ printf(_("Ringtone number: %d\n"), profile.Ringtone);
+
+ printf(_("Ringing volume: %s\n"), GetProfileVolumeString(profile.Volume));
+
+ printf(_("Message alert tone: %s\n"), GetProfileMessageToneString(profile.MessageTone));
+
+ printf(_("Keypad tones: %s\n"), GetProfileKeypadToneString(profile.KeypadTone));
+
+ printf(_("Warning and game tones: %s\n"), GetProfileWarningToneString(profile.WarningTone));
+
+ if (GetModelFeature (FN_SCREENSAVER)!=0)
+ printf(_("Screen saver: %s\n"), GetProfileOnOffString(profile.ScreenSaver));
+
+ printf(_("Vibration: %s\n"), GetProfileVibrationString(profile.Vibration));
+
+ /* It has been nice to add here reading caller group name. ;^) */
+ if (GetModelFeature (FN_CALENDAR)==F_CAL71)
+ printf(_("Caller groups: %s\n"),
+ GetProfileCallerGroups(profile.CallerGroups) );
+
+ /* FIXME: need make investigation for 3310 for these features. For now unknown */
+ if (GetModelFeature (FN_PROFILES)!=F_PROF33) {
+ /* FIXME: Light settings is only used for Car */
+ if (profile.Number==(max_profiles-2)) printf(_("Lights: %s\n"), profile.Lights ? _("On") : _("Automatic"));
+
+ /* FIXME: Automatic answer is only used for Car and Headset. */
+ if (profile.Number>=(max_profiles-2)) printf(_("Automatic answer: %s\n"), GetProfileOnOffString(profile.AutomaticAnswer));
+ }
+
+ printf("\n");
+
+ i++;
+ }
+ } else {
+ if (error == GE_NOTIMPLEMENTED) {
+ fprintf(stderr, _("Function not implemented in %s model!\n"), model);
+ GSM->Terminate();
+ return -1;
+ } else
+ {
+ fprintf(stderr, _("Unspecified error\n"));
+ GSM->Terminate();
+ return -1;
+ }
+ }
+
+ GSM->Terminate();
+
+ return 0;
+
+}
+
+/* Sets profile feature */
+
+int setprofile(int argc, char *argv[])
+{
+
+/* Hopefully is 64 larger as FB38_MAX* / FB61_MAX* */
+ char model[64], rev[64];
+
+ int max_profiles;
+ GSM_Profile profile;
+ GSM_Profile profile2, profile3;
+ GSM_Error error;
+ bool correct_arg1;
+ bool correct_arg2;
+
+/* Initialise the code for the GSM interface. */
+
+ fbusinit(NULL);
+
+ profile.Number = 0;
+
+ error = GSM->GetProfile(&profile);
+
+ if (error == GE_NONE)
+ {
+
+ while (GSM->GetModel(model) != GE_NONE) sleep(1);
+
+ while (GSM->GetRevision(rev) != GE_NONE) sleep(1);
+
+ strncpy(rev,rev+2,5);
+ rev[5]=0;
+ PrepareRingingTones(model,rev);
+
+ switch(GetModelFeature (FN_PROFILES)) {
+ case F_PROF33:max_profiles=6;break;
+ case F_PROF51:max_profiles=3;break;
+ default :max_profiles=7;break;
+ }
+
+ profile.Number=atoi (argv[0]);
+ profile.Number=profile.Number-1;
+
+ if (profile.Number < 0)
+ {
+ fprintf(stderr, _("Profile number must be value from 1 to %i!\n"), max_profiles);
+ GSM->Terminate();
+ return -1;
+ }
+
+ if (profile.Number >= max_profiles)
+ {
+ fprintf(stderr, _("This phone supports only %i profiles!\n"), max_profiles);
+ GSM->Terminate();
+ return -1;
+ }
+
+ if (profile.Number!=0) GSM->GetProfile(&profile);
+
+ correct_arg1=false;
+ correct_arg2=false;
+
+ if (strcmp(argv[1], "callalert")==0)
+ {
+ if (strcmp(argv[2], "ringing")==0) {profile.CallAlert=PROFILE_CALLALERT_RINGING;correct_arg2=true;}
+ if (strcmp(argv[2], "ascending")==0) {profile.CallAlert=PROFILE_CALLALERT_ASCENDING;correct_arg2=true;}
+ if (strcmp(argv[2], "ringonce")==0) {profile.CallAlert=PROFILE_CALLALERT_RINGONCE;correct_arg2=true;}
+ if (strcmp(argv[2], "beeponce")==0) {profile.CallAlert=PROFILE_CALLALERT_BEEPONCE;correct_arg2=true;}
+ if (strcmp(argv[2], "groups")==0)
+ {
+ profile.CallAlert=PROFILE_CALLALERT_CALLERGROUPS;
+ correct_arg2=true;
+ /*Ignored by N5110*/
+ /*FIX ME: it's ignored by N5130 and 3210 too*/
+ if (max_profiles==3) fprintf(stdout, _("Warning: value \"groups\" for profile feature \"callalert\" will be ignored in this phone model !\n"));
+ }
+ if (strcmp(argv[2], "off")==0 || strcmp(argv[2], "0")==0) {profile.CallAlert=PROFILE_CALLALERT_OFF;correct_arg2=true;}
+ if (!correct_arg2)
+ {
+ fprintf(stderr, _("Correct parameters for profile feature \"callalert\" are ringing|ascending|ringonce|beeponce|groups|off|0 !\n"));
+ GSM->Terminate();
+ return -1;
+ }
+ correct_arg1=true;
+ }
+ if (strcmp(argv[1], "volume")==0)
+ {
+ if (strcmp(argv[2], "1")==0) {profile.Volume=PROFILE_VOLUME_LEVEL1;correct_arg2=true;}
+ if (strcmp(argv[2], "2")==0) {profile.Volume=PROFILE_VOLUME_LEVEL2;correct_arg2=true;}
+ if (strcmp(argv[2], "3")==0) {profile.Volume=PROFILE_VOLUME_LEVEL3;correct_arg2=true;}
+ if (strcmp(argv[2], "4")==0) {profile.Volume=PROFILE_VOLUME_LEVEL4;correct_arg2=true;}
+ if (strcmp(argv[2], "5")==0) {profile.Volume=PROFILE_VOLUME_LEVEL5;correct_arg2=true;}
+ if (!correct_arg2)
+ {
+ fprintf(stderr, _("Correct parameters for profile feature \"volume\" are 0|1|2|3|4|5 !\n"));
+ GSM->Terminate();
+ return -1;
+ }
+ correct_arg1=true;
+ }
+ if (strcmp(argv[1], "keypad")==0 || strcmp(argv[1], "keypadtone")==0)
+ {
+ if (strcmp(argv[2], "0")==0 || strcmp(argv[2], "off")==0) {profile.KeypadTone=PROFILE_KEYPAD_OFF;correct_arg2=true;}
+ if (strcmp(argv[2], "1")==0) {profile.KeypadTone=PROFILE_KEYPAD_LEVEL1;correct_arg2=true;}
+ if (strcmp(argv[2], "2")==0) {profile.KeypadTone=PROFILE_KEYPAD_LEVEL2;correct_arg2=true;}
+ if (strcmp(argv[2], "3")==0) {profile.KeypadTone=PROFILE_KEYPAD_LEVEL3;correct_arg2=true;}
+ if (!correct_arg2)
+ {
+ fprintf(stderr, _("Correct parameters for profile feature \"keypad|keypadtone\" are off|0|1|2|3 !\n"));
+ GSM->Terminate();
+ return -1;
+ }
+ correct_arg1=true;
+ }
+ if (strcmp(argv[1], "messagetone")==0 || strcmp(argv[1], "smstone")==0 || strcmp(argv[1], "sms")==0 || strcmp(argv[1], "message")==0)
+ {
+ if (strcmp(argv[2], "0")==0 || strcmp(argv[2], "off")==0) {profile.MessageTone=PROFILE_MESSAGE_NOTONE;correct_arg2=true;}
+ if (strcmp(argv[2], "standard")==0) {profile.MessageTone=PROFILE_MESSAGE_STANDARD;correct_arg2=true;}
+ if (strcmp(argv[2], "special")==0) {profile.MessageTone=PROFILE_MESSAGE_SPECIAL;correct_arg2=true;}
+ if (strcmp(argv[2], "beeponce")==0 || strcmp(argv[2], "once")==0) {profile.MessageTone=PROFILE_MESSAGE_BEEPONCE;correct_arg2=true;}
+ if (strcmp(argv[2], "ascending")==0) {profile.MessageTone=PROFILE_MESSAGE_ASCENDING;correct_arg2=true;}
+ if (!correct_arg2)
+ {
+ fprintf(stderr, _("Correct parameters for profile feature \"messagetone|smstone|message|sms\" are 0|off|standard|special|beeponce|once|ascending !\n"));
+ GSM->Terminate();
+ return -1;
+ }
+ correct_arg1=true;
+ }
+ if (strcmp(argv[1], "warningtone")==0 || strcmp(argv[1], "warning")==0)
+ {
+ if (strcmp(argv[2], "0")==0 || strcmp(argv[2], "off")==0) {profile.WarningTone=PROFILE_WARNING_OFF;correct_arg2=true;}
+ if (strcmp(argv[2], "1")==0 || strcmp(argv[2], "on")==0) {profile.WarningTone=PROFILE_WARNING_ON;correct_arg2=true;}
+ if (!correct_arg2)
+ {
+ fprintf(stderr, _("Correct parameters for profile feature \"warningtone|warning\" are 0|off|1|on !\n"));
+ GSM->Terminate();
+ return -1;
+ }
+ correct_arg1=true;
+ }
+ if (strcmp(argv[1], "vibra")==0 || strcmp(argv[1], "vibration")==0)
+ {
+ if (strcmp(argv[2], "0")==0 || strcmp(argv[2], "off")==0) {profile.Vibration=PROFILE_VIBRATION_OFF;correct_arg2=true;}
+ if (strcmp(argv[2], "1")==0 || strcmp(argv[2], "on")==0) {profile.Vibration=PROFILE_VIBRATION_ON;correct_arg2=true;}
+ if (!correct_arg2)
+ {
+ fprintf(stderr, _("Correct parameters for profile feature \"vibration|vibra\" are 0|off|1|on !\n"));
+ GSM->Terminate();
+ return -1;
+ }
+ correct_arg1=true;
+ }
+ if (strcmp(argv[1], "lights")==0)
+ {
+ if (strcmp(argv[2], "0")==0 || strcmp(argv[2], "off")==0) {profile.Lights=-1;correct_arg2=true;}
+ if (strcmp(argv[2], "1")==0 || strcmp(argv[2], "on")==0) {profile.Lights=0;correct_arg2=true;}
+ if (!correct_arg2)
+ {
+ fprintf(stderr, _("Correct parameters for profile feature \"lights\" are 0|off|1|on !\n"));
+ GSM->Terminate();
+ return -1;
+ }
+ if (profile.Number!=(max_profiles-2))
+ {
+ profile2.Number=max_profiles-2;
+ if (GSM->GetProfile(&profile2)==GE_NONE)
+ {
+ fprintf(stdout, _("Warning: \"Lights\" feature is ignored in this profile (only setting it for \"%s\" profile get some results) !\n"), profile2.Name);
+ }
+ }
+ correct_arg1=true;
+ }
+ if (strcmp(argv[1], "answer")==0)
+ {
+ if (strcmp(argv[2], "0")==0 || strcmp(argv[2], "off")==0) {profile.AutomaticAnswer=-1;correct_arg2=true;}
+ if (strcmp(argv[2], "1")==0 || strcmp(argv[2], "on")==0) {profile.AutomaticAnswer=0;correct_arg2=true;}
+ if (!correct_arg2)
+ {
+ fprintf(stderr, _("Correct parameters for profile feature \"answer\" are 0|off|1|on !\n"));
+ GSM->Terminate();
+ return -1;
+ }
+ if (profile.Number<(max_profiles-2))
+ {
+ profile2.Number=max_profiles-2;
+ if (GSM->GetProfile(&profile2)==GE_NONE)
+ {
+ profile3.Number=max_profiles-1;
+ if (GSM->GetProfile(&profile3)==GE_NONE)
+ {
+ fprintf(stdout, _("Warning: \"Automatic Answer\" feature is ignored in this profile (only setting it for \"%s\" and \"%s\" profiles get some results) !\n"), profile2.Name, profile3.Name);
+ }
+ }
+ }
+ correct_arg1=true;
+ }
+ if (strcmp(argv[1], "name")==0)
+ {
+ strcpy(profile.Name,argv[2]);
+ /*Ignored by N5110*/
+ /*FIX ME: it's ignored by N5130 and 3210 too*/
+ if (max_profiles==3) fprintf(stdout, _("Warning: this phone model doesn't allow to change profile name !\n"));
+ correct_arg1=true;
+ }
+ if (strcmp(argv[1], "ringtone")==0)
+ {
+ profile.Ringtone=atoi(argv[2]);
+ if (profile.Ringtone<1)
+ {
+ /*With value 0 results are interesting in N5110, but can't be used for anything*/
+ fprintf(stderr, _("Ringtone number must be higher than 0 !\n"));
+ GSM->Terminate();
+ return -1;
+ } else
+ {
+ if (profile.Ringtone>NumberOfRingtones())
+ {
+ fprintf(stderr, _("Ringtone number too high (max %i) !\n"),NumberOfRingtones());
+ GSM->Terminate();
+ return -1;
+ }
+ profile.Ringtone=RingingToneCode(profile.Ringtone);
+ if (profile.Ringtone==0)
+ {
+ fprintf(stderr, _("Warning: we don't know ringtones codes for this model ! Can you contact with gnokii authors to add it into source ?\n"));
+ GSM->Terminate();
+ return -1;
+ }
+ if (max_profiles==3) fprintf(stdout, _("Warning: ringtone is changed for all profiles. You must reset phone or select profile in phone againg to see result.\n"));
+ }
+ correct_arg1=true;
+ }
+ if (strcmp(argv[1], "groups")==0)
+ {
+ /*Ignored by N5110*/
+ /*FIX ME: it's ignored by N5130 and 3210 too*/
+ if (max_profiles==3) fprintf(stdout, _("Warning: this phone model doesn't allow to change caller group name !\n"));
+ profile.CallerGroups=atoi(argv[2]);
+ correct_arg1=true;
+ }
+
+ if (!correct_arg1)
+ {
+ fprintf(stderr, _("Correct profile feature names are callalert|volume|keypad|keypadtone|messagetone|smstone|message|sms|warningtone|warning|vibra|vibration|lights|answer|name|groups !\n"));
+ GSM->Terminate();
+ return -1;
+ }
+
+ GSM->SetProfile(&profile);
+
+ } else {
+ if (error == GE_NOTIMPLEMENTED) {
+ fprintf(stderr, _("Function not implemented in %s model!\n"), model);
+ GSM->Terminate();
+ return -1;
+ } else
+ {
+ fprintf(stderr, _("Unspecified error\n"));
+ GSM->Terminate();
+ return -1;
+ }
+ }
+
+ GSM->Terminate();
+
+ return 0;
+
+}
+
+/* Get requested range of memory storage entries and output to stdout in
+ easy-to-parse format */
+
+int getmemory(int argc, char *argv[])
+{
+
+ GSM_PhonebookEntry entry;
+ int count;
+ register int i;
+ GSM_Error error;
+ GSM_Bitmap bitmap;
+ char memory_type_string[20];
+ int start_entry;
+ int end_entry;
+ int i_used = 0, n_used=0;
+ int do_all;
+ char *output_opt = NULL;
+ bool wasdate=false;
+ char az_group_name[5][MAX_BITMAP_TEXT_LENGTH];
+ bool formatdone=false;
+ char buf[64];
+
+ /* group names init */
+ for(i=0;i<5;i++) az_group_name[i][0]='\0';
+
+ /* Handle command line args that set type, start and end locations. */
+ if (!GetMemoryTypeID(argv[0], &entry.MemoryType))
+ {
+ fprintf(stderr, _("Unknown memory type %s!\n"), argv[0]);
+ return (-1);
+ }
+ GetMemoryTypeString(memory_type_string, &entry.MemoryType);
+
+ if (argv[argc-1][0] == '-')
+ output_opt = argv[--argc];
+
+ /* Do generic initialisation routine */
+
+ fbusinit(NULL);
+
+ while ((error = GSM->GetModel(buf)) != GE_NONE && i++ < 15)
+ sleep(1);
+
+ if (argc > 1) {
+ do_all = 0;
+ start_entry = atoi (argv[1]);
+ end_entry = argc > 2 ? atoi( argv[2]) : start_entry;
+ } else {
+ GSM_MemoryStatus stats = {entry.MemoryType, 0, 0};
+
+ do_all = 1;
+ start_entry = 1;
+ if (GSM->GetMemoryStatus( &stats) != GE_NONE) {
+ fprintf( stderr, _("Error reading memory status.\n"));
+ GSM->Terminate();
+ return -1;
+ }
+ n_used = stats.Used;
+ end_entry = stats.Used + stats.Free;
+ }
+
+
+ /* Now retrieve the requested entries. */
+
+ for (count = start_entry;
+ count <= end_entry && (!do_all || i_used < n_used);
+ count++) {
+
+ entry.Location=count;
+
+ error=GSM->GetMemoryLocation(&entry);
+
+ switch (error) {
+ case GE_NONE:
+ if (entry.SubEntriesCount || strcmp( entry.Number, ""))
+ i_used++;
+ else if (do_all)
+ break;
+ if (output_opt && !strcmp( output_opt,"-v30")) {
+ semicolon_pipe_substitution( &entry, 0 );
+ fprintf(stdout,_("%s"),GSM_GetVCARD(&entry,30));
+ formatdone=true;
+ }
+ if (output_opt && !strcmp(output_opt,"-v21")) {
+ semicolon_pipe_substitution( &entry, 0 );
+ fprintf(stdout,_("%s"),GSM_GetVCARD(&entry,21));
+ formatdone=true;
+ }
+ if (output_opt && !strcmp(output_opt,"-v")) {
+ semicolon_pipe_substitution( &entry, 0 );
+ fprintf(stdout,_("%s"),GSM_GetVCARD(&entry,10));
+ formatdone=true;
+ }
+ if (output_opt && !strcmp(output_opt,"-short")) {
+ semicolon_pipe_substitution( &entry, 0 );
+ fprintf(stdout, "%s;%s;%s;%d;%d;", entry.Name, entry.Number, memory_type_string, entry.Location, entry.Group);
+ for( i = 0; i < entry.SubEntriesCount; i++ )
+ {
+ if( entry.SubEntries[i].EntryType == GSM_Date )
+ fprintf(stdout,_("%u;%u;%u;%02u.%02u.%04u;%02u:%02u:%02u;"),
+ entry.SubEntries[i].EntryType,
+ entry.SubEntries[i].NumberType,
+ entry.SubEntries[i].BlockNumber,
+ entry.SubEntries[i].data.Date.Day,
+ entry.SubEntries[i].data.Date.Month,
+ entry.SubEntries[i].data.Date.Year,
+ entry.SubEntries[i].data.Date.Hour,
+ entry.SubEntries[i].data.Date.Minute,
+ entry.SubEntries[i].data.Date.Second );
+ else
+ fprintf(stdout,_("%u;%u;%u;%s;"),
+ entry.SubEntries[i].EntryType,
+ entry.SubEntries[i].NumberType,
+ entry.SubEntries[i].BlockNumber,
+ entry.SubEntries[i].data.Number );
+ }
+ fprintf(stdout,_("\n"));
+ formatdone=true;
+ }
+ if (!formatdone) {
+ char z_gtype[12];
+ wasdate=false;
+ fprintf(stdout, "Memory %s, location %d\n",memory_type_string, entry.Location);
+
+ // check if some info in subentries
+ for( i = 0; i < entry.SubEntriesCount; i++ )
+ if( entry.SubEntries[i].EntryType != GSM_Date &&
+ strcmp(entry.SubEntries[i].data.Number,"") )
+ break;
+
+ if (strcmp(entry.Number,"") || i < entry.SubEntriesCount) {
+ if (strcmp(entry.Name,"")) fprintf(stdout,_(" Name: %s\n"),entry.Name);
+ if (strcmp(entry.Number,"")) fprintf(stdout,_(" Number: %s\n"),entry.Number);
+ bitmap.type=GSM_CallerLogo;
+ bitmap.number=entry.Group;
+ strcpy(z_gtype,"unknown");
+ if (entry.Group==5) strcpy(z_gtype,"No group");
+ if (entry.Group<5 && entry.Group>=0) {
+ if (!strcmp(az_group_name[entry.Group],"")) {
+ if (GetModelFeature (FN_CALLERGROUPS)!=0) {
+ if (GSM->GetBitmap(&bitmap)==GE_NONE)
+ strcpy( az_group_name[entry.Group], bitmap.text );
+ }
+ if ((!strcmp(az_group_name[entry.Group],""))) {
+ switch(entry.Group) {
+ case 0:strcpy(az_group_name[entry.Group],"Family");break;
+ case 1:strcpy(az_group_name[entry.Group],"VIP");break;
+ case 2:strcpy(az_group_name[entry.Group],"Friends");break;
+ case 3:strcpy(az_group_name[entry.Group],"Colleagues");break;
+ case 4:strcpy(az_group_name[entry.Group],"Other");break;
+ default:break;
+ }
+ }
+ }
+ strcpy(z_gtype,az_group_name[entry.Group]);
+ }
+ fprintf(stdout,_(" Group: %d (%s)\n"),entry.Group+1,z_gtype);
+ for( i = 0; i < entry.SubEntriesCount; i++ )
+ {
+ if( entry.SubEntries[i].EntryType == GSM_Date ) {
+ fprintf(stdout, " Date and time: %s %02u.%02u.%04u %02u:%02u:%02u\n",
+ DayOfWeek(entry.SubEntries[i].data.Date.Year,
+ entry.SubEntries[i].data.Date.Month,
+ entry.SubEntries[i].data.Date.Day),
+ entry.SubEntries[i].data.Date.Day,
+ entry.SubEntries[i].data.Date.Month,
+ entry.SubEntries[i].data.Date.Year,
+ entry.SubEntries[i].data.Date.Hour,
+ entry.SubEntries[i].data.Date.Minute,
+ entry.SubEntries[i].data.Date.Second);
+ wasdate=true;
+ } else {
+ if( strcmp(entry.SubEntries[i].data.Number,"") ) {
+ char z_etype[19];
+ switch( entry.SubEntries[i].EntryType ) {
+ case GSM_Number:
+ switch( entry.SubEntries[i].NumberType ) {
+ case GSM_General: strcpy(z_etype,"General "); break;
+ case GSM_Home: strcpy(z_etype,"Home "); break;
+ case GSM_Mobile: strcpy(z_etype,"Mobile "); break;
+ case GSM_Work: strcpy(z_etype,"Work "); break;
+ case GSM_Fax: strcpy(z_etype,"Fax "); break;
+ default: strcpy(z_etype,""); break;
+ }
+ strcat(z_etype,"Number"); break;
+ case GSM_Note:
+ strcpy(z_etype,"Note"); break;
+ case GSM_Postal:
+ strcpy(z_etype,"Postal"); break;
+ case GSM_Email:
+ strcpy(z_etype,"E-Mail"); break;
+ default:
+ strcpy(z_etype,"unknown data"); break;
+ }
+#ifdef DEBUG
+ fprintf(stdout,_(" ---> Subentry: %u\n"),i+1);
+ fprintf(stdout,_(" Entry type: %u (%s)\n"),entry.SubEntries[i].EntryType,z_etype);
+ fprintf(stdout,_(" Number type: %u\n"),entry.SubEntries[i].NumberType);
+ fprintf(stdout,_(" Block Number: %u\n"),entry.SubEntries[i].BlockNumber);
+#endif
+ fprintf(stdout,_(" %s: %s\n"),z_etype,entry.SubEntries[i].data.Number);
+ }
+ }
+ }
+ if ((entry.MemoryType==GMT_DC ||
+ entry.MemoryType==GMT_RC ||
+ entry.MemoryType==GMT_MC) && !wasdate)
+ fprintf(stdout,_(" Date and time not available\n"));
+ } else
+ fprintf(stdout,_(" Location empty\n"));
+ }
+ break;
+ case GE_NOTIMPLEMENTED:
+ fprintf( stderr, _("Function not implemented in %s model!\n"), model);
+ GSM->Terminate();
+ return -1;
+ case GE_INVALIDMEMORYTYPE:
+ fprintf( stderr, _("Memory type %s not supported!\n"),
+ memory_type_string);
+ GSM->Terminate();
+ return -1;
+ default:
+ fprintf(stdout, _("%s|%d|Bad location or other error!(%d)\n"),
+ memory_type_string, count, error);
+ }
+ }
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+/* Read data from stdin, parse and write to phone. The parsing is relatively
+ crude and doesn't allow for much variation from the stipulated format. */
+
+int writephonebook(int argc, char *args[])
+{
+
+ GSM_PhonebookEntry entry;
+ GSM_Error error;
+ char *memory_type_string;
+ int line_count=0,current,i;
+ int subentry;
+
+ char *Line, OLine[1024], BackLine[1024];
+ char *ptr;
+
+ /* Check argument */
+ if (argc) {
+ if (strcmp("-i", args[0])) {
+ usage();
+ return 0;
+ }
+ }
+ /* Initialise fbus code */
+
+ fbusinit(NULL);
+
+ Line = OLine;
+
+ /* Go through data from stdin. */
+
+ while (GetLine(stdin, Line, sizeof(OLine))!=-1) {
+
+ current=0;BackLine[current++]=Line[0];
+ for (i=1;i<strlen(Line);i++) {
+ if (Line[i-1]==';' && Line[i]==';') BackLine[current++]=' ';
+ BackLine[current++]=Line[i];
+ }
+ BackLine[current++]=0;
+
+ strcpy(Line,BackLine);
+
+ line_count++;
+
+#if defined(__svr4__) || defined(__FreeBSD__)
+ ptr=strtok(Line, ";"); if (ptr) strcpy(entry.Name, ptr);
+
+ entry.Number[0]=0;
+ ptr=strtok(NULL, ";"); if (ptr && ptr[0]!=' ') strcpy(entry.Number, ptr);
+
+ ptr=strtok(NULL, ";");
+#else
+ ptr=strsep(&Line, ";"); if (ptr) strcpy(entry.Name, ptr);
+
+ entry.Number[0]=0;
+ ptr=strsep(&Line, ";"); if (ptr && ptr[0]!=' ') strcpy(entry.Number, ptr);
+
+ ptr=strsep(&Line, ";");
+#endif
+
+ if (!ptr) {
+ fprintf(stderr, _("Format problem on line %d [%s] 1\n"), line_count, BackLine);
+ Line = OLine;
+ continue;
+ }
+
+ if (!strncmp(ptr,"ME", 2))
+ {
+ memory_type_string = "int";
+ entry.MemoryType = GMT_ME;
+ }
+ else if (!strncmp(ptr,"SM", 2))
+ {
+ memory_type_string = "sim";
+ entry.MemoryType = GMT_SM;
+ }
+ else
+ {
+ fprintf(stderr, _("Format problem on line %d [%s] 2: %s\n"),
+ line_count, BackLine,ptr);
+ break;
+ }
+
+#if defined(__svr4__) || defined(__FreeBSD__)
+ ptr=strtok(NULL, ";"); if (ptr) entry.Location=atoi(ptr);
+
+ ptr=strtok(NULL, ";"); if (ptr) entry.Group=atoi(ptr);
+#else
+ ptr=strsep(&Line, ";"); if (ptr) entry.Location=atoi(ptr);
+
+ ptr=strsep(&Line, ";"); if (ptr) entry.Group=atoi(ptr);
+#endif
+
+ if (!ptr) {
+ fprintf(stderr, _("Format problem on line %d [%s] 3\n"),
+ line_count, BackLine);
+ continue;
+ }
+
+ for( subentry = 0; ; subentry++ )
+ {
+#if defined(__svr4__) || defined(__FreeBSD__)
+ ptr=strtok(NULL, ";");
+#else
+ ptr=strsep(&Line, ";");
+#endif
+ if( ptr && *ptr != 0 )
+ entry.SubEntries[subentry].EntryType=atoi(ptr);
+ else
+ break;
+
+#if defined(__svr4__) || defined(__FreeBSD__)
+ ptr=strtok(NULL, ";");
+#else
+ ptr=strsep(&Line, ";");
+#endif
+ if(ptr)
+ entry.SubEntries[subentry].NumberType=atoi(ptr);
+ // Phone Numbers need to have a number type.
+ if(!ptr && entry.SubEntries[subentry].EntryType == GSM_Number)
+ {
+ fprintf(stderr, _("Missing phone number type on line %d"
+ " entry %d [%s]\n"), line_count, subentry, BackLine);
+ subentry--;
+ break;
+ }
+
+#if defined(__svr4__) || defined(__FreeBSD__)
+ ptr=strtok(NULL, ";");
+#else
+ ptr=strsep(&Line, ";");
+#endif
+ if(ptr)
+ entry.SubEntries[subentry].BlockNumber=atoi(ptr);
+
+#if defined(__svr4__) || defined(__FreeBSD__)
+ ptr=strtok(NULL, ";");
+#else
+ ptr=strsep(&Line, ";");
+#endif
+ // 0x13 Date Type; it is only for Dailed Numbers, etc.
+ // we don't store to this memories so it's an error to use it.
+ if(!ptr || entry.SubEntries[subentry].EntryType == GSM_Date)
+ {
+ fprintf(stderr, _("Is not a phone number on line %d entry %d [%s]\n"),
+ line_count, subentry, BackLine);
+ subentry--;
+ break;
+ }
+ else
+ strcpy( entry.SubEntries[subentry].data.Number, ptr );
+ }
+
+ entry.SubEntriesCount = subentry;
+
+
+ /* This is to send other exports (like from 6110) to 7110 */
+ if (!entry.SubEntriesCount) {
+ entry.SubEntriesCount = 1;
+ entry.SubEntries[subentry].EntryType = GSM_Number;
+ entry.SubEntries[subentry].NumberType = GSM_General;
+ entry.SubEntries[subentry].BlockNumber = 2;
+ strcpy(entry.SubEntries[subentry].data.Number, entry.Number);
+ }
+
+ Line = OLine;
+
+ if (argc) {
+ GSM_PhonebookEntry tmp_entry;
+
+ memcpy(&tmp_entry, &entry, sizeof(GSM_PhonebookEntry) );
+ error = GSM->GetMemoryLocation(&tmp_entry);
+ if (error == GE_NONE) {
+ if (!tmp_entry.Empty) {
+ int confirm = -1;
+ char ans[8];
+ FILE *input_flow; //for reading from console, even when input redir.
+
+ input_flow = fopen(DEV_CONSOLE, "r");
+
+ if (!input_flow) {
+ fprintf(stderr, _("Can't open \"%s\" for input !\n"),DEV_CONSOLE);
+ return(-1);
+ }
+
+ fprintf(stderr, _("Location busy. "));
+ while (confirm < 0) {
+ fprintf(stderr, _("Overwrite? (yes/no) "));
+ GetLine(input_flow, ans, 7);
+ if (!strcmp(ans, "yes")) confirm = 1;
+ else if (!strcmp(ans, "no")) confirm = 0;
+ }
+ if (!confirm) continue;
+ }
+ } else {
+ fprintf(stderr, _("Unknown error (%d)\n"), error);
+ GSM->Terminate();
+ return 0;
+ }
+ }
+
+ /* Do write and report success/failure. */
+ semicolon_pipe_substitution( &entry, 1 );
+
+ error = GSM->WritePhonebookLocation(&entry);
+
+ if (error == GE_NONE)
+ fprintf (stdout, _("Write Succeeded: memory type: %s, loc: %d, name: %s, number: %s\n"), memory_type_string, entry.Location, entry.Name, entry.Number);
+ else
+ fprintf (stdout, _("Write FAILED(%d): memory type: %s, loc: %d, name: %s, number: %s\n"), error, memory_type_string, entry.Location, entry.Name, entry.Number);
+
+ }
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+/* Getting speed dials. */
+
+int getspeeddial(char *Number) {
+
+ GSM_SpeedDial entry;
+ GSM_Error error;
+ GSM_PhonebookEntry pbentry;
+
+ entry.Number = atoi(Number);
+
+ fbusinit(NULL);
+
+ if (GSM->GetSpeedDial(&entry)==GE_NONE) {
+ pbentry.Location=entry.Location;
+ if (pbentry.Location==0) pbentry.Location=entry.Number;
+ pbentry.MemoryType=entry.MemoryType;
+
+ error=GSM->GetMemoryLocation(&pbentry);
+
+ if (error == GE_NONE)
+ {
+ fprintf(stdout, _("SpeedDial nr. %d: %d:%d (%s)\n"), entry.Number, entry.MemoryType, entry.Location,pbentry.Name);
+ } else
+ fprintf(stdout, _("Error\n"));
+ } else {
+ fprintf(stdout, _("Error\n"));
+ }
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+/* Setting speed dials. */
+
+int setspeeddial(char *argv[]) {
+
+ GSM_SpeedDial entry;
+
+ char *memory_type_string;
+
+ /* Handle command line args that set type, start and end locations. */
+
+ if (strcmp(argv[1], "ME") == 0) {
+ entry.MemoryType = GMT_ME;
+ memory_type_string = "ME";
+ }
+ else if (strcmp(argv[1], "SM") == 0) {
+ entry.MemoryType = GMT_SM;
+ memory_type_string = "SM";
+ }
+ else {
+ fprintf(stderr, _("Unknown memory type %s!\n"), argv[1]);
+
+ return -1;
+ }
+
+ entry.Number = atoi(argv[0]);
+ entry.Location = atoi(argv[2]);
+
+ fbusinit(NULL);
+
+ if (GSM->SetSpeedDial(&entry) == GE_NONE) {
+ fprintf(stdout, _("Succesfully written!\n"));
+ }
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+/* Getting the status of the display. */
+
+int getdisplaystatus()
+{
+
+ int Status;
+
+ /* Initialise the code for the GSM interface. */
+
+ fbusinit(NULL);
+
+ if (GSM->GetDisplayStatus(&Status)==GE_NONE) {
+
+ printf(_("Call in progress: %s\n"), Status & (1<<DS_Call_In_Progress)?_("on"):_("off"));
+ printf(_("Unknown: %s\n"), Status & (1<<DS_Unknown)?_("on"):_("off"));
+ printf(_("Unread SMS: %s\n"), Status & (1<<DS_Unread_SMS)?_("on"):_("off"));
+ printf(_("Voice call: %s\n"), Status & (1<<DS_Voice_Call)?_("on"):_("off"));
+ printf(_("Fax call active: %s\n"), Status & (1<<DS_Fax_Call)?_("on"):_("off"));
+ printf(_("Data call active: %s\n"), Status & (1<<DS_Data_Call)?_("on"):_("off"));
+ printf(_("Keyboard lock: %s\n"), Status & (1<<DS_Keyboard_Lock)?_("on"):_("off"));
+ printf(_("SMS storage full: %s\n"), Status & (1<<DS_SMS_Storage_Full)?_("on"):_("off"));
+
+ } else {
+ printf(_("Error\n"));
+ }
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+int netmonitor(char *Mode)
+{
+
+ unsigned char mode=atoi(Mode);
+ char Screen[NM_MAX_SCREEN_WIDTH];
+ int i;
+
+ fbusinit(NULL);
+
+ if (!strcmp(Mode,"reset")) mode=0xf0;
+ else if (!strcmp(Mode,"off")) mode=0xf1;
+ else if (!strcmp(Mode,"field"))mode=0xf2;
+ else if (!strcmp(Mode,"devel"))mode=0xf3;
+ else if (!strcmp(Mode,"next")) mode=0x00;
+
+ /* We clear it */
+ for (i=0;i<NM_MAX_SCREEN_WIDTH;i++) Screen[i]=0;
+
+ GSM->NetMonitor(mode, Screen);
+
+ if (Screen)
+ printf("%s\n", Screen);
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+int identify( void )
+{
+ /* Hopefully is 64 larger as FB38_MAX* / FB61_MAX* */
+ char imei[64], model[64], rev[64], manufacturer[64];
+
+ fbusinit(NULL);
+
+ while (GSM->GetIMEI(imei) != GE_NONE) sleep(1);
+ while (GSM->GetRevision(rev) != GE_NONE) sleep(1);
+ while (GSM->GetModel(model) != GE_NONE) sleep(1);
+
+ strcpy(manufacturer, "(unknown)");
+ GSM->GetManufacturer(manufacturer);
+
+ fprintf(stdout, _("IMEI: %s\n"), imei);
+ fprintf(stdout, _("Model: %s %s (%s)\n"), manufacturer, GetModelName (model), model);
+ fprintf(stdout, _("Revision: %s\n"), rev);
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+int senddtmf(char *String)
+{
+
+ fbusinit(NULL);
+
+ if (GSM->SendDTMF(String)!=GE_NONE) fprintf(stdout,_("Error!\n"));
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+/* Resets the phone */
+int reset(int argc, char *argv[])
+{
+
+ unsigned char _type=0x03;
+
+ if (argc>0) {
+ _type=0x10;
+
+ if (!strcmp(argv[0],"soft")) _type = 0x03;
+
+ /* Doesn't work with 5110 */
+ if (!strcmp(argv[0],"hard")) _type = 0x04;
+
+ if (_type==0x10) {
+ fprintf(stderr, _("What kind of reset do you want (second parameter can be \"soft\" or \"hard\") ?\n"));
+ return -1;
+ }
+ }
+
+ fbusinit(NULL);
+
+ GSM->Reset(_type);
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+/* This is a "convenience" function to allow quick test of new API stuff which
+ doesn't warrant a "proper" command line function. */
+
+int foogle(char *argv[])
+{
+ /* Initialise the code for the GSM interface. */
+
+ fbusinit(NULL);
+
+ // Fill in what you would like to test here...
+
+ sleep(5);
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+int phonetests()
+{
+ /* Initialise the code for the GSM interface. */
+
+ fbusinit(NULL);
+
+ if (GSM->PhoneTests()!=GE_NONE) fprintf(stderr,_("Error\n"));
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+/* pmon allows fbus code to run in a passive state - it doesn't worry about
+ whether comms are established with the phone. A debugging/development
+ tool. */
+
+int pmon()
+{
+
+ GSM_Error error;
+ GSM_ConnectionType connection=GCT_FBUS;
+
+ /* Initialise the code for the GSM interface. */
+
+ error = GSM_Initialise(model, Port, Initlength, connection, RLP_DisplayF96Frame, SynchronizeTime);
+
+ if (error != GE_NONE) {
+ fprintf(stderr, _("GSM/FBUS init failed! (Unknown model ?). Quitting.\n"));
+ return -1;
+ }
+
+
+ while (1) {
+ usleep(50000);
+ }
+
+ return 0;
+}
+
+int setringtone(int argc, char *argv[])
+{
+ GSM_Ringtone ringtone;
+ GSM_BinRingtone binringtone,binringtone2;
+
+ GSM_Error error;
+
+ int current=0; //number of packed notes or location
+ int i;
+
+ char model[64];
+
+ /* If not binary ringtone */
+ if (GSM_ReadBinRingtoneFile(argv[0],&binringtone2)!=GE_NONE) {
+ fprintf(stdout,_("Not binary ringtone, trying RTTL\n"));
+
+ if (GSM_ReadRingtoneFileOnConsole(argv[0], &ringtone)!=GE_NONE) return(-1);
+
+ ringtone.location=1;
+ if (argc>1) ringtone.location=atoi(argv[1]);
+
+ ringtone.allnotesscale=false;
+
+ /* Initialise the GSM interface. */
+ fbusinit(NULL);
+
+ while (GSM->GetModel(model) != GE_NONE)
+ sleep(1);
+
+ /* For Nokia 6110/6130/6150/6210 we use different method of uploading.
+ Phone will display menu, when received it */
+ if ( !strcmp(model,"NSE-3") || !strcmp(model,"NSK-3") ||
+ !strcmp(model,"NSM-1") || !strcmp(model,"NPE-3") ) {
+ if (argc==1) ringtone.location=255;
+ }
+
+ error=GSM->SetRingtone(&ringtone,¤t);
+
+ if (current!=ringtone.NrNotes) {
+ if (current>FB61_MAX_RINGTONE_NOTES) {
+ fprintf(stderr,_("Warning: due to phone limitation"));
+ } else {
+ fprintf(stderr,_("Warning: ringtone was too long to be saved into frame,"));
+ }
+ fprintf(stderr, _(" only %i first notes were packed (%i cut)\n"),current,ringtone.NrNotes-current);
+ }
+
+ if (error==GE_NONE)
+ fprintf(stdout, _("Set succeeded!\n"));
+ else
+ fprintf(stdout, _("Setting failed\n"));
+
+ } else { /* This IS binary ringtone */
+ fprintf(stdout,_("Binary ringtone format\n"));
+
+ if (argc==3) {
+ binringtone.frame[current++]=0x00;
+ binringtone.frame[current++]=0x00;
+ binringtone.frame[current++]=0x0c;
+ binringtone.frame[current++]=0x01;
+ binringtone.frame[current++]=0x2c;
+
+ //copy new name
+ memcpy(binringtone.frame+current,argv[2],strlen(argv[2]));
+ current=current+strlen(argv[2]);
+
+ /*don't use old*/
+ i=2;
+ while(binringtone2.frame[i]!=0x00) {
+ if (i==binringtone.length) break;
+ i++;
+ }
+
+ //copy binringtone
+ memcpy(binringtone.frame+current,binringtone2.frame+i,binringtone2.length-i);
+ binringtone.length=binringtone2.length-i+current;
+ } else
+ {
+ memcpy(binringtone.frame+current,binringtone2.frame,binringtone2.length);
+ binringtone.length=binringtone2.length;
+ }
+
+ binringtone.location=1;
+ if (argc>1) binringtone.location=atoi(argv[1]);
+
+ /* Initialise the GSM interface. */
+ fbusinit(NULL);
+
+ error=GSM->SetBinRingtone(&binringtone);
+
+ switch (error) {
+ case GE_NONE:
+ fprintf(stdout, _("Set succeeded!\n"));
+ break;
+ case GE_INVALIDRINGLOCATION:
+ fprintf(stdout, _("Invalid location %i!\n"),binringtone.location);
+ break;
+ case GE_UNKNOWNMODEL:
+ fprintf(stdout, _("Mygnokii doesn't know format for this model!\n"));
+ break;
+ case GE_NOTIMPLEMENTED:
+ fprintf(stdout, _("Not implemented for this model!\n"));
+ break;
+ default:
+ fprintf(stdout, _("Not supported by this model!\n"));
+ break;
+ }
+ }
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+int ringtoneconvert(int argc, char *argv[])
+{
+ GSM_Ringtone ringtone;
+
+ if (!strcmp(argv[0],argv[1]))
+ {
+ fprintf(stderr, _("Files can't have the same names !\n"));
+ return -1;
+ }
+
+ if (GSM_ReadRingtoneFileOnConsole(argv[0], &ringtone)!=GE_NONE) return(-1);
+
+ ringtone.allnotesscale=false;
+
+ GSM_SaveRingtoneFileOnConsole(argv[1], &ringtone);
+
+ return 0;
+}
+
+int playringtone(int argc, char *argv[])
+{
+ GSM_Ringtone ringtone;
+
+ GSM_BinRingtone binringtone;
+
+ int i,j,z;
+ int Hz;
+ bool isok;
+
+//{ "c", "c#", "d", "d#", "e", "f", "f#", "g", "g#", "a", "a#", "h" };
+ int binary_notes[12] =
+ { 0, 1, 2, 3, 4, 6, 7, 8, 9, 10, 11 , 12};
+
+ if (GSM_ReadBinRingtoneFile(argv[0],&binringtone)!=GE_NONE) {
+ fprintf(stdout,_("Not binary ringtone, trying RTTL\n"));
+
+ if (GSM_ReadRingtoneFileOnConsole(argv[0], &ringtone)!=GE_NONE) return(-1);
+
+ /* Initialise the GSM interface. */
+ fbusinit(NULL);
+
+ fprintf(stdout,_("Playing \"%s\" (%i notes)\n"),ringtone.name,ringtone.NrNotes);
+
+ GSM_PlayRingtoneOnConsole(&ringtone);
+
+ } else {
+
+ fprintf(stdout,_("Binary ringtone format\n"));
+
+ /* Initialise the GSM interface. */
+ fbusinit(NULL);
+
+ i=5;
+ while (true) { //skipping name
+ if (binringtone.frame[i]==0) break;
+ i++;
+ }
+
+ i=i+5;j=0;z=0;
+ while (true) {
+ if (binringtone.frame[i]!=j) {
+ if (j!=0) {
+//#ifdef DEBUG
+ fprintf(stdout,_("Block in binary ringtone %i %i\n"),j,z);
+//#endif
+ isok=false;
+ if (j==64) {
+ j=255;//Pause
+ isok=true;
+ }
+ if (!isok && j>=114 && j<=125) {
+ j=14*3+binary_notes[j-114];
+ isok=true;
+ }
+ if (!isok && j>=126 && j<=137) {
+ j=14*1+binary_notes[j-126];
+ isok=true;
+ }
+ if (!isok && j>=138 && j<=149) {
+ j=14*2+binary_notes[j-138];
+ isok=true;
+ }
+ if (!isok && j>=150 && j<=161) {
+ j=14*4+binary_notes[j-150];
+ isok=true;
+ }
+ if (!isok) {
+//#ifdef DEBUG
+ fprintf(stdout,_("Unknown block in binary ringtone %i %i\n"),j,z);
+//#endif
+ } else {
+ Hz=GSM_GetFrequency(j);
+ if (GSM->PlayTone(Hz,5)!=GE_NONE) fprintf(stdout,_("error during playing\n"));
+ usleep(z*5000);
+ }
+ }
+ j=binringtone.frame[i];
+ z=binringtone.frame[i+1];
+ } else {
+ z=z+binringtone.frame[i+1];
+ }
+ i=i+2;
+ if (i>=binringtone.length) break;
+ }
+
+ GSM->PlayTone(0,0);
+ }
+
+ GSM->Terminate();
+
+ return 0;
+}
+
+int composer(int argc, char *argv[])
+{
+ GSM_Ringtone ringtone;
+ int i;
+ bool unknown;
+ int oldnoteslen=4,nownoteslen,oldnoteslen2;
+ int oldnotesscale=1,nownotesscale;
+ bool firstnote=true;
+ int DefNoteTempo=63;
+
+ if (GSM_ReadRingtoneFileOnConsole(argv[0], &ringtone)!=GE_NONE) return(-1);
+
+ if (ringtone.NrNotes!=0)
+ DefNoteTempo=ringtone.notes[0].tempo;
+
+ fprintf(stdout,_("Ringtone \"%s\" (tempo = %i Beats Per Minute)\n\n"),ringtone.name,GSM_GetTempo(DefNoteTempo));
+
+ for (i=0;i<ringtone.NrNotes;i++) {
+ if (DefNoteTempo!=ringtone.notes[i].tempo) {
+ fprintf(stdout,_("WARNING: IN FACT RINGTONE HAS DIFFERENT TEMPO FOR DIFFERENT NOTES AND THAT'S WHY YOU CAN'T ENTER IT ALL IN THE COMPOSITOR\n\n"));
+ break;
+ }
+ }
+
+ for (i=0;i<ringtone.NrNotes;i++) {
+
+ if (firstnote) {
+ if (GSM_GetNote(ringtone.notes[i].note)!=Note_Pause)
+ firstnote=false;
+ }
+
+ if (!firstnote) {
+ break;
+ }
+
+ }
+
+ if ((ringtone.NrNotes-i)>50)
+ fprintf(stdout,_("WARNING: LENGTH=%i, BUT YOU WILL ENTER ONLY FIRST 50 TONES. TO ENTER FULL RINGTONE MUST SEND IT (--sendringtone) OR DOWNLOAD (--setringtone)\n\n"),ringtone.NrNotes-i);
+
+ fprintf(stdout,_("This ringtone in Nokia Composer in phone should look: "));
+
+ firstnote=true;
+
+ for (i=0;i<ringtone.NrNotes;i++) {
+
+ if (firstnote) {
+ if (GSM_GetNote(ringtone.notes[i].note)!=Note_Pause)
+ firstnote=false;
+ }
+
+ if (!firstnote) {
+
+ switch (ringtone.notes[i].duration) {
+ case 192:fprintf(stdout,_("1."));break; //192=128*1.5
+ case 128:fprintf(stdout,_("1"));break;
+ case 96 :fprintf(stdout,_("2."));break; //96=64*1.5
+ case 64 :fprintf(stdout,_("2"));break;
+ case 48 :fprintf(stdout,_("4."));break; //48=32*1.5
+ case 32 :fprintf(stdout,_("4"));break;
+ case 24 :fprintf(stdout,_("8."));break; //24=16*1.5
+ case 16 :fprintf(stdout,_("8"));break;
+ case 12 :fprintf(stdout,_("16."));break; //12=8*1.5
+ case 8 :fprintf(stdout,_("16"));break;
+ case 6 :fprintf(stdout,_("32."));break; //6=4*1.5
+ case 4 :fprintf(stdout,_("32"));break;
+ }
+
+ unknown=false;
+
+ /* What note here ? */
+ switch (GSM_GetNote(ringtone.notes[i].note)) {
+ case Note_C :fprintf(stdout,_("c"));break;
+ case Note_Cis:fprintf(stdout,_("#c"));break;
+ case Note_D :fprintf(stdout,_("d"));break;
+ case Note_Dis:fprintf(stdout,_("#d"));break;
+ case Note_E :fprintf(stdout,_("e"));break;
+ case Note_F :fprintf(stdout,_("f"));break;
+ case Note_Fis:fprintf(stdout,_("#f"));break;
+ case Note_G :fprintf(stdout,_("g"));break;
+ case Note_Gis:fprintf(stdout,_("#g"));break;
+ case Note_A :fprintf(stdout,_("a"));break;
+ case Note_Ais:fprintf(stdout,_("#a"));break;
+ case Note_H :fprintf(stdout,_("h"));break;
+ default :fprintf(stdout,_("-"));unknown=true;break; //Pause ?
+ }
+
+ if (!unknown)
+ fprintf(stdout,_("%i"),ringtone.notes[i].note/14);
+
+ /* And separator before next note */
+ if (i!=ringtone.NrNotes-1)
+ fprintf(stdout,_(" "));
+
+ }
+
+ }
+
+ fprintf(stdout,_("\n\nTo enter it please press: "));
+
+ firstnote=true;
+
+ for (i=0;i<ringtone.NrNotes;i++) {
+
+ if (firstnote) {
+ if (GSM_GetNote(ringtone.notes[i].note)!=Note_Pause)
+ firstnote=false;
+ }
+
+ if (!firstnote) {
+
+ unknown=false;
+
+ /* What note here ? */
+ switch (GSM_GetNote(ringtone.notes[i].note)) {
+ case Note_C :fprintf(stdout,_("1"));break;
+ case Note_Cis:fprintf(stdout,_("1"));break;
+ case Note_D :fprintf(stdout,_("2"));break;
+ case Note_Dis:fprintf(stdout,_("2"));break;
+ case Note_E :fprintf(stdout,_("3"));break;
+ case Note_F :fprintf(stdout,_("4"));break;
+ case Note_Fis:fprintf(stdout,_("4"));break;
+ case Note_G :fprintf(stdout,_("5"));break;
+ case Note_Gis:fprintf(stdout,_("5"));break;
+ case Note_A :fprintf(stdout,_("6"));break;
+ case Note_Ais:fprintf(stdout,_("6"));break;
+ case Note_H :fprintf(stdout,_("7"));break;
+ default :fprintf(stdout,_("0"));unknown=true;break;
+ }
+
+ switch (ringtone.notes[i].duration) {
+ case 192:fprintf(stdout,_("(longer)"));break; //192=128*1.5
+ case 96 :fprintf(stdout,_("(longer)"));break; //96=64*1.5
+ case 48 :fprintf(stdout,_("(longer)"));break; //48=32*1.5
+ case 24 :fprintf(stdout,_("(longer)"));break; //24=16*1.5
+ case 12 :fprintf(stdout,_("(longer)"));break; //12=8*1.5
+ case 6 :fprintf(stdout,_("(longer)"));break; //6=4*1.5
+ default:break;
+ }
+
+ /* What note here ? */
+ switch (GSM_GetNote(ringtone.notes[i].note)) {
+ case Note_Cis:fprintf(stdout,_("#"));break;
+ case Note_Dis:fprintf(stdout,_("#"));break;
+ case Note_Fis:fprintf(stdout,_("#"));break;
+ case Note_Gis:fprintf(stdout,_("#"));break;
+ case Note_Ais:fprintf(stdout,_("#"));break;
+ default :break;
+ }
+
+ if (!unknown)
+ {
+ nownotesscale=ringtone.notes[i].note/14;
+
+ if (nownotesscale!=oldnotesscale) {
+ switch (nownotesscale) {
+ case 1:
+ switch (oldnotesscale) {
+ case 2:fprintf(stdout,_("**"));break;
+ case 3:fprintf(stdout,_("*"));break;
+ }
+ break;
+ case 2:
+ switch (oldnotesscale) {
+ case 1:fprintf(stdout,_("*"));break;
+ case 3:fprintf(stdout,_("**"));break;
+ }
+ break;
+ case 3:
+ switch (oldnotesscale) {
+ case 1:fprintf(stdout,_("**"));break;
+ case 2:fprintf(stdout,_("*"));break;
+ }
+ break;
+ }
+ }
+
+ oldnotesscale=nownotesscale;
+ }
+
+ nownoteslen=0;
+ oldnoteslen2=oldnoteslen;
+
+ switch (ringtone.notes[i].duration) {
+ case 192:nownoteslen=1;break; //192=128*1.5
+ case 128:nownoteslen=1;break;
+ case 96 :nownoteslen=2;break; //96=64*1.5
+ case 64 :nownoteslen=2;break;
+ case 48 :nownoteslen=4;break; //48=32*1.5
+ case 32 :nownoteslen=4;break;
+ case 24 :nownoteslen=8;break; //24=16*1.5
+ case 16 :nownoteslen=8;break;
+ case 12 :nownoteslen=16;break; //12=8*1.5
+ case 8 :nownoteslen=16;break;
+ case 6 :nownoteslen=32;break; //6=4*1.5
+ case 4 :nownoteslen=32;break;
+ }
+
+ if (nownoteslen>oldnoteslen) {
+ while (oldnoteslen!=nownoteslen) {
+ fprintf(stdout,_("8"));
+ oldnoteslen=oldnoteslen*2;
+ }
+ }
+
+ if (nownoteslen<oldnoteslen) {
+ while (oldnoteslen!=nownoteslen) {
+ fprintf(stdout,_("9"));
+ oldnoteslen=oldnoteslen/2;
+ }
+ }
+
+ if (GSM_GetNote(ringtone.notes[i].note)==Note_Pause)
+ oldnoteslen=oldnoteslen2;
+
+ /* And separator before next note */
+ if (i!=ringtone.NrNotes-1)
+ fprintf(stdout,_(" "));
+
+ }
+ }
+
+ fprintf(stdout,_("\n"));
+
+ return 0;
+
+}
+
+int sendringtone(int argc, char *argv[])
+{
+ GSM_Ringtone ringtone;
+ GSM_MultiSMSMessage SMS;
+ int current,i;
+ bool ProfileStyle=false; /* If we use profile style available in new Nokia models */
+
+ if (GSM_ReadRingtoneFileOnConsole(argv[1], &ringtone)!=GE_NONE) return(-1);
+
+ ringtone.allnotesscale=false;
+
+ for (i=0;i<argc;i++) {
+ if (!strcmp(argv[i],"--profilestyle")) ProfileStyle=true;
+ if (!strcmp(argv[i],"--scale")) ringtone.allnotesscale=true;
+ }
+
+ current=GSM_SaveRingtoneToSMS(&SMS,&ringtone,ProfileStyle);
+
+ if (current!=ringtone.NrNotes) {
+ if (current>FB61_MAX_RINGTONE_NOTES) {
+ fprintf(stderr,_("Warning: due to phone limitation"));
+ } else {
+ fprintf(stderr,_("Warning: ringtone was too long to be saved into SMS,"));
+ }
+ fprintf(stderr, _(" only %i first notes were packed (%i cut)\n"),current,ringtone.NrNotes-current);
+ }
+
+ for (i=0;i<SMS.number;i++) {
+ strcpy(SMS.SMS[i].Destination,argv[0]);
+ }
+
+ /* Initialise the GSM interface. */
+ fbusinit(NULL);
+
+ GSM_SendMultiPartSMSOnConsole(&SMS, 2,argc,argv,false,true,true);
+
+ return 0;
+}
+
+int saveringtone(int argc, char *argv[])
+{
+ GSM_Ringtone ringtone;
+ GSM_MultiSMSMessage SMS;
+ int current,i;
+ bool ProfileStyle=false; /* If we use profile style available in new Nokia models */
+
+ if (GSM_ReadRingtoneFileOnConsole(argv[0], &ringtone)!=GE_NONE) return(-1);
+
+ ringtone.allnotesscale=false;
+
+ for (i=0;i<argc;i++) {
+ if (!strcmp(argv[i],"--profilestyle")) ProfileStyle=true;
+ if (!strcmp(argv[i],"--scale")) ringtone.allnotesscale=true;
+ }
+
+ current=GSM_SaveRingtoneToSMS(&SMS,&ringtone,ProfileStyle);
+
+ if (current!=ringtone.NrNotes) {
+ if (current>FB61_MAX_RINGTONE_NOTES) {
+ fprintf(stderr,_("Warning: due to phone limitation"));
+ } else {
+ fprintf(stderr,_("Warning: ringtone was too long to be saved into SMS,"));
+ }
+ fprintf(stderr, _(" only %i first notes were packed (%i cut)\n"),current,ringtone.NrNotes-current);
+ }
+
+ for (i=0;i<SMS.number;i++) {
+ /* Only 11 chars could be here */
+ strncpy(SMS.SMS[i].Destination,ringtone.name,11);
+ }
+
+ /* Initialise the GSM interface. */
+ fbusinit(NULL);
+
+ GSM_SaveMultiPartSMSOnConsole(&SMS,1,argc,argv,false,false,true,true);
+
+ return 0;
+}
+
+/* Converts logo files. */
+
+int bitmapconvert(int argc, char *argv[])
+{
+ GSM_Bitmap bitmap;
+ GSM_NetworkInfo NetworkInfo;
+ bool doit;
+ int num;
+
+ if (!strcmp(argv[0],argv[1]))
+ {
+ fprintf(stderr, _("Files can't have the same names !\n"));
+ return -1;
+ }
+
+ if (GSM_ReadBitmapFileOnConsole(argv[0], &bitmap)!=GE_NONE) return(-1);
+
+ if (argc>2)
+ {
+ doit=false;
+ if (!strcmp(argv[2],"op"))
+ {
+ doit=false;
+ if (argc<4) doit=true;
+ if (argc<4 && bitmap.type!=GSM_OperatorLogo) doit=true;
+ if (doit)
+ {
+ fbusinit(NULL);
+ if (GSM->GetNetworkInfo(&NetworkInfo) == GE_NONE) strncpy(bitmap.netcode,NetworkInfo.NetworkCode,7);
+ GSM->Terminate();
+ }
+ GSM_ResizeBitmap(&bitmap,GSM_OperatorLogo);
+ if (argc==4)
+ {
+ strncpy(bitmap.netcode,argv[3],7);
+ if (!strcmp(GSM_GetNetworkName(bitmap.netcode),"unknown"))
+ {
+ fprintf(stderr,"Sorry, gnokii doesn't know \"%s\" network !\n",bitmap.netcode);
+ return -1;
+ }
+ }
+ doit=true;
+ }
+ if (!strcmp(argv[2],"7110op"))
+ {
+ doit=false;
+ if (argc<4) doit=true;
+ if (argc<4 && bitmap.type!=GSM_7110OperatorLogo) doit=true;
+ if (doit)
+ {
+ fbusinit(NULL);
+ if (GSM->GetNetworkInfo(&NetworkInfo) == GE_NONE) strncpy(bitmap.netcode,NetworkInfo.NetworkCode,7);
+ GSM->Terminate();
+ }
+ GSM_ResizeBitmap(&bitmap,GSM_7110OperatorLogo);
+ if (argc==4)
+ {
+ strncpy(bitmap.netcode,argv[3],7);
+ if (!strcmp(GSM_GetNetworkName(bitmap.netcode),"unknown"))
+ {
+ fprintf(stderr,"Sorry, gnokii doesn't know \"%s\" network !\n",bitmap.netcode);
+ return -1;
+ }
+ }
+ doit=true;
+ }
+ if (!strcmp(argv[2],"caller"))
+ {
+ GSM_ResizeBitmap(&bitmap,GSM_CallerLogo);
+ if (argc>3)
+ {
+ num=argv[3][0]-'0';
+ if ((num<0)||(num>9)) num=0;
+ bitmap.number=num;
+ } else
+ {
+ bitmap.number=0;
+ }
+ doit=true;
+ }
+ if (!strcmp(argv[2],"startup"))
+ {
+ GSM_ResizeBitmap(&bitmap,GSM_StartupLogo);
+ doit=true;
+ }
+ if (!strcmp(argv[2],"7110startup"))
+ {
+ GSM_ResizeBitmap(&bitmap,GSM_7110StartupLogo);
+ doit=true;
+ }
+ if (!strcmp(argv[2],"6210startup"))
+ {
+ GSM_ResizeBitmap(&bitmap,GSM_6210StartupLogo);
+ doit=true;
+ }
+ if (!strcmp(argv[2],"picture"))
+ {
+ GSM_ResizeBitmap(&bitmap,GSM_PictureImage);
+ doit=true;
+ }
+ if (!doit)
+ {
+ fprintf(stderr,"Unknown type of logo: %s !\n",argv[2]);
+ return -1;
+ }
+ }
+
+ if (GSM_SaveBitmapFileOnConsole(argv[1], &bitmap)!=GE_NONE) return(-1);
+
+ return 0;
+}
+
+int getphoneprofile()
+{
+ GSM_PPS PPS;
+ GSM_Error error;
+
+ /* Initialise the GSM interface. */
+ fbusinit(NULL);
+
+ PPS.Name=PPS_ALS;
+ error=GSM->GetProductProfileSetting(&PPS);
+ if (error!=GE_NONE) {
+ fprintf(stdout,_("Error!\n"));
+ GSM->Terminate();
+ return -1;
+ }
+ fprintf(stdout,_("ALS : "));
+ if (PPS.bool_value) fprintf(stdout,_("on\n"));
+ else fprintf(stdout,_("off\n"));
+
+ PPS.Name=PPS_VibraMenu;
+ GSM->GetProductProfileSetting(&PPS);
+ fprintf(stdout,_("Vibra menu : "));
+ if (PPS.bool_value) fprintf(stdout,_("on\n"));
+ else fprintf(stdout,_("off\n"));
+
+ PPS.Name=PPS_GamesMenu;
+ GSM->GetProductProfileSetting(&PPS);
+ fprintf(stdout,_("Games menu : "));
+ if (PPS.bool_value) fprintf(stdout,_("on\n"));
+ else fprintf(stdout,_("off\n"));
+
+ PPS.Name=PPS_HRData;
+ GSM->GetProductProfileSetting(&PPS);
+ fprintf(stdout,_("HR Data : "));
+ if (PPS.bool_value) fprintf(stdout,_("on\n"));
+ else fprintf(stdout,_("off\n"));
+
+ PPS.Name=PPS_14400Data;
+ GSM->GetProductProfileSetting(&PPS);
+ fprintf(stdout,_("14400 Data : "));
+ if (PPS.bool_value) fprintf(stdout,_("on\n"));
+ else fprintf(stdout,_("off\n"));
+
+ PPS.Name=PPS_LCDContrast;
+ GSM->GetProductProfileSetting(&PPS);
+ fprintf(stdout,_("LCD Contrast : %i%%\n"),PPS.int_value);
+
+ PPS.Name=PPS_EFR;
+ GSM->GetProductProfileSetting(&PPS);
+ fprintf(stdout,_("EFR : "));
+ switch (PPS.int_value) {
+ case 0: fprintf(stdout,_("off\n")); break;
+ case 1: fprintf(stdout,_("last\n")); break;
+ case 2: fprintf(stdout,_("second\n"));break;
+ case 3: fprintf(stdout,_("first\n")); break;
+ }
+
+ PPS.Name=PPS_FR;
+ GSM->GetProductProfileSetting(&PPS);
+ fprintf(stdout,_("FR : "));
+ switch (PPS.int_value) {
+ case 0: fprintf(stdout,_("off\n")); break;
+ case 1: fprintf(stdout,_("last\n")); break;
+ case 2: fprintf(stdout,_("second\n"));break;
+ case 3: fprintf(stdout,_("first\n")); break;
+ }
+
+ PPS.Name=PPS_HR;
+ GSM->GetProductProfileSetting(&PPS);
+ fprintf(stdout,_("HR : "));
+ switch (PPS.int_value) {
+ case 0: fprintf(stdout,_("off\n")); break;
+ case 1: fprintf(stdout,_("last\n")); break;
+ case 2: fprintf(stdout,_("second\n"));break;
+ case 3: fprintf(stdout,_("first\n")); break;
+ }
+
+ GSM->Terminate();
+
+ return 0;
+
+}
+
+int setphoneprofile(int argc, char *argv[])
+{
+ GSM_PPS PPS;
+ GSM_Error error;
+ bool correct_arg1=false, correct_arg2=false;
+
+ if (!strcmp(argv[0],"ALS")) {
+ PPS.Name=PPS_ALS;
+ correct_arg1=true;
+ if (!strcmp(argv[1],"1")) {
+ PPS.bool_value=true;
+ correct_arg2=true;
+ }
+ if (!strcmp(argv[1],"0")) {
+ PPS.bool_value=false;
+ correct_arg2=true;
+ }
+ if (!correct_arg2) {
+ fprintf(stdout,_("Settings for ALS parameter can be \"0\" or \"1\" !\n"));
+ return -1;
+ }
+ }
+ if (!strcmp(argv[0],"HRData")) {
+ PPS.Name=PPS_HRData;
+ correct_arg1=true;
+ if (!strcmp(argv[1],"1")) {
+ PPS.bool_value=true;
+ correct_arg2=true;
+ }
+ if (!strcmp(argv[1],"0")) {
+ PPS.bool_value=false;
+ correct_arg2=true;
+ }
+ if (!correct_arg2) {
+ fprintf(stdout,_("Settings for HRData parameter can be \"0\" or \"1\" !\n"));
+ return -1;
+ }
+ }
+ if (!correct_arg1) {
+ fprintf(stdout,_("First parameter can be \"ALS\" or \"HRData\" only !\n"));
+ return -1;
+ }
+
+ /* Initialise the GSM interface. */
+ fbusinit(NULL);
+
+ error=GSM->SetProductProfileSetting(&PPS);
+
+ if (error!=GE_NONE) {
+ fprintf(stdout,_("Error!\n"));
+ GSM->Terminate();
+ return -1;
+ }
+
+ GSM->Reset(0x03);
+
+ GSM->Terminate();
+
+ return 0;
+
+}
+
+int getoperatorname()
+{
+
+ GSM_Network network;
+
+ /* Initialise the GSM interface. */
+ fbusinit(NULL);
+
+ if (GSM->GetOperatorName(&network)==GE_NONE)
+ {
+ if (!strcmp(network.Name,"")) {
+ fprintf(stdout,_("Phone doesn't have downloaded operator name\n"));
+ } else {
+ fprintf(stdout,_("Phone has downloaded operator name (\"%s\") for \"%s\" (\"%s\") network\n"),
+ network.Name,network.Code,GSM_GetNetworkName(network.Code));
+ }
+ }
+
+ GSM->Terminate();
+
+ return 0;
+
+}
+
+int setoperatorname(int argc, char *argv[])
+{
+
+ GSM_Network network;
+
+ /* Initialise the GSM interface. */
+ fbusinit(NULL);
+
+ if (argc==2) {
+ strncpy(network.Code,argv[0],7);
+ strncpy(network.Name,argv[1],50);
+ } else {
+ strcpy(network.Code,"000 00\0");
+ strcpy(network.Name,"\0");
+ }
+
+ if (GSM->SetOperatorName(&network)==GE_NONE) {
+ if (GSM->GetOperatorName(&network)==GE_NONE) {
+ if (!strcmp(network.Name,"")) {
+ fprintf(stdout,_("Downloaded operator name is removed\n"));
+ } else {
+ fprintf(stdout,_("Downloaded operator name changed for \"%s\" network (\"%s\") to \"%s\"\n"),
+ network.Code,GSM_GetNetworkName(network.Code),network.Name);
+ }
+ }
+ }
+
+ GSM->Terminate();
+
+ return 0;
+
+}
+
+int getvoicemailbox()
+{
+ GSM_PhonebookEntry entry;
+
+ /* Initialise the GSM interface. */
+ fbusinit(NULL);
+
+ if (GSM->GetVoiceMailbox(&entry)==GE_NONE) {
+ fprintf(stdout,_("Voice mailbox number is "));
+ if (!strcmp(entry.Number,""))
+ fprintf(stdout,_("not set\n"));
+ else
+ fprintf(stdout,_("\"%s\"\n"),entry.Number);
+ }
+
+ GSM->Terminate();
+
+ return 0;
+
+}
+
+///////////////////////////////////////////////////////////////////////////////
+// flow diagram of netmonitordata():
+///////////////////////////////////////////////////////////////////////////////
+//
+// get command line argument
+// |
+// v
+//
+// if specific phone model
+// use that model
+// else
+// identify-phone: (((((((( TO DO )))))))))))))
+//
+// |
+// v
+// get_mon_param_info() get phone netmonitor parameters name
+// specifically to a 'model'
+// |
+// v
+// parse_check() check command line arguments
+// | if all OK, go on else stop.
+// | because we can have a input file
+// v containing multiple
+// parse_process() command lines, we process each at once
+// so we can exit early on errors.
+//
+///////////////////////////////////////////////////////////////////////////////
+
+// private functions, see netmonitordata()
+void free_nm_info(PARAM_INFO_MON *info)
+{
+ PARAM_INFO_MON *tmp; // pointer, iterator on info
+
+ // go to end of list
+
+ while (info->next != NULL)
+ { tmp = info->next;
+ free(info->name);
+ free(info->mname);
+ free(info);
+ info = tmp;
+ }
+ free(info);
+}
+
+///////////////////////////////////////////////////////////////////////////////
+// this func retrieve parameters info from a file
+// and load it in a dynamic array, NULL terminated,
+// if 2rd parameter is not NULL, it load also description of screen
+// return (PARAM_INFO_MON *start) if all is OK, else NULL
+///////////////////////////////////////////////////////////////////////////////
+// start->->next->next->next-> ...->next->NULL
+// | | | | |
+// V V V V V
+// par0 par1 par2 parN
+///////////////////////////////////////////////////////////////////////////////
+// this should be de-allocated from calling function,
+// also, screen_name should be deallocated from calling function
+///////////////////////////////////////////////////////////////////////////////
+
+PARAM_INFO_MON *get_mon_param_info(char *f_name, char *screen_name[NM_MAX_SCREEN+1])
+{
+ PARAM_INFO_MON *start; // pointer to netmonitor parameters info
+ PARAM_INFO_MON *info; // pointer, iterator on info
+ PARAM_INFO_MON *check; // pointer, iterator on info, for check usage
+
+ FILE *f_info;
+
+ char buf[256];
+ char *param;
+ char *param_name;
+ char *tmp;
+
+ char tmp_mname[55]; // very larger, but if netmon bug ...
+ int x, y, len, s, t; // x & y coord, len, screen nr, type
+ int i;
+
+ if (screen_name != NULL)
+ for (i = 0; i <= NM_MAX_SCREEN; i++)
+ screen_name[i] = NULL;
+
+
+ if ((f_info = fopen(f_name, "r")) == NULL)
+ { fprintf(stderr, "Can' t open file parameter info: <%s>\n", f_name);
+ return(NULL);
+ }
+
+ if ((start = malloc(sizeof(PARAM_INFO_MON))) == NULL)
+ { fprintf(stderr, "no mem\n");
+ return(NULL);
+ }
+ else
+ { start->next = NULL;
+ }
+
+ info = start;
+ while (fgets(buf, 256, f_info) != NULL)
+ {
+ param = buf;
+
+ // Truncate from '#' at right of comments
+ if ((tmp = strchr(param, '#')) != NULL)
+ *tmp = '\0';
+
+ // Strip leading, trailing whitespace
+ while(isspace((int) *param))
+ param++;
+
+ while((strlen(param) > 0) && isspace((int) param[strlen(param) - 1]))
+ param[strlen(param) - 1] = '\0';
+
+ // Ignore blank lines
+ if ((*param == '\n') || (*param == '\0'))
+ continue;
+
+
+#ifdef DEBUG
+ fprintf(stderr, "%s: info line: <%s>\n", f_name, param);
+#endif
+ // check for param name
+ if ((param_name = strtok(param, "=\t\n")) == NULL)
+ continue;
+
+ // check if screen name
+ if (strncmp("SCREEN", param_name, 6) == 0)
+ {
+ // if we do not want screen names ...
+ if (screen_name == NULL)
+ continue;
+
+// FIXME check for screen nr
+ if ((tmp = strtok(NULL, ":\n")) == NULL)
+ continue;
+
+ i = atoi(tmp);
+// FIXME: check if already defined screen
+
+ if ((i <= 0) || (i > NM_MAX_SCREEN))
+ continue;
+ // check for screen name
+ if ((tmp = strtok(NULL, ":\n")) == NULL)
+ continue;
+
+ screen_name[i] = strdup(tmp);
+ }
+ else
+ {
+ // parameter
+
+// FIXME: check for NM_MAX_FIELDS
+
+ // check for x coord
+ if ((tmp = strtok(NULL, ":\t\n")) == NULL)
+ continue;
+ x = atoi(tmp);
+
+ // check for y coord
+ if ((tmp = strtok(NULL, ":\t\n")) == NULL)
+ continue;
+ y = atoi(tmp);
+
+ // check for len
+ if ((tmp = strtok(NULL, ":\t\n")) == NULL)
+ continue;
+ len = atoi(tmp);
+
+ // check for screen
+ if ((tmp = strtok(NULL, ":\t\n")) == NULL)
+ continue;
+ s = atoi(tmp);
+
+ // check for netmon manual name
+ if ((tmp = strtok(NULL, ":\t\n")) == NULL)
+ { fprintf(stderr,
+ "%s: PARAMETER <%s> in screen <%d>, not have netmon manual reference\n",
+ f_name, param_name, s);
+ free_nm_info(start);
+ return(NULL);
+ }
+ strcpy(tmp_mname, tmp);
+
+ // check for data type (optional)
+ if ((tmp = strtok(NULL, ":\t\n")) != NULL)
+ t = *tmp;
+ else
+ t = '\0';
+
+ // check len, here, so we print parameter name
+ if (len == 0)
+ { fprintf(stderr,
+ "%s: PARAMETER <%s> in screen <%d>, has invalid data lenght\n",
+ f_name, param_name, s);
+ free_nm_info(start);
+ return(NULL);
+ }
+
+ // check if already defined same param_name
+ check = start;
+ while (check->next != NULL)
+ { check = check->next;
+ if (strcmp(param_name, check->name) == 0)
+ {
+ fprintf(stderr,
+ "%s: PARAMETER <%s> in screen <%d> already defined as in screen <%d>\n",
+ f_name, param_name, s, check->s_nr);
+ free_nm_info(start);
+ return(NULL);
+ }
+ }
+
+ // make space, and add parameter
+ if ((info->next = malloc(sizeof(PARAM_INFO_MON))) != NULL)
+ {
+ info = info->next;
+ info->name = strdup(param_name);
+ info->x = x;
+ info->y = y;
+ info->len = len;
+ info->s_nr = s;
+ info->mname = strdup(tmp_mname);
+ info->type = t;
+
+ info->next = NULL; // mark end
+ }
+ else
+ {
+ fprintf(stderr, "no mem");
+ free_nm_info(start);
+ return(NULL);
+ }
+
+ }
+
+ }
+
+ fclose(f_info);
+
+#ifdef DEBUG
+ info = start;
+ while (info->next != NULL)
+ {
+ info = info->next;
+ fprintf(stderr, "info name %s\n", info->name);
+ }
+#endif
+ return(start);
+}
+
+// 2, parse the arguments and check command(s) line
+// command line, phone spec input, and output are complex,
+// so we exit printing info about error instead of std help
+///////////////////////////////////////////////////////////////////////////////
+
+int parse_check(int argc, char *argv[], PARAM_INFO_MON *start, char *f_name, int line)
+{
+ int ctr;
+ int i;
+ int time_spec;
+ int found_data;
+ char *p;
+ char *tmp;
+ char *o;
+ PARAM_INFO_MON *info; // iterator on this list
+
+#ifdef DEBUG
+ for (i = 0; i < argc; i++)
+ fprintf(stderr, "argv[%d] = <%s>\n",i, argv[i]);
+#endif
+
+ time_spec = 0;
+ ctr = 0;
+ i = 0;
+ while (i < argc)
+ {
+ p = argv[i];
+ if (*p == '-')
+ { // should be one of the short option
+ if (strcmp(argv[i], "-fs") == 0)
+ { // field separator, next arg should be a string
+ if (((i+1) < argc) && (strlen(argv[i+1]) < 10))
+ { i++;
+ // arg OK, do nothing
+ }
+ else
+ { if (line)
+ fprintf(stderr,
+ "-fs: Invalid field separator in <%s> at line %d\n",
+ f_name, line);
+ else
+ fprintf(stderr, "-fs: Invalid field separator\n");
+ return(-1);
+ }
+ }
+ else if (strcmp(argv[i], "-ls") == 0)
+ { // line separator, next arg should be a string
+ if (((i+1) < argc) && (strlen(argv[i+1]) < 10))
+ { i++;
+ // arg OK, do nothing
+ }
+ else
+ { if (line)
+ fprintf(stderr,
+ "-ls: Invalid line separator in <%s> at line %d\n",
+ f_name, line);
+ else
+ fprintf(stderr, "-ls: Invalid line separator\n");
+ return(-1);
+ }
+ }
+ else if (strcmp(argv[i], "-tm") == 0)
+ { // time separator, next arg should be a millisecond (200-10000)
+ if (time_spec)
+ { if (line)
+ fprintf(stderr,
+ "-tm, -ts, are mutually exclusive in <%s> at line %d\n",
+ f_name, line);
+ else
+ fprintf(stderr, "-tm, -ts, are mutually exclusive\n");
+ return(-1);
+ }
+
+ if (((i+1) < argc) && (atoi(argv[i+1]) >= 200) && (atoi(argv[i+1]) <= 10000))
+ { i++;
+ time_spec = 1;
+ // arg OK, do nothing
+ }
+ else
+ { if (line)
+ fprintf(stderr,
+ "-tm: Invalid argument (200-10000 milliseconds), in <%s> at line %d\n",
+ f_name, line);
+ else
+ fprintf(stderr, "-tm: Invalid argument (200-10000 milliseconds)\n");
+ return(-1);
+ }
+ }
+ else if (strcmp(argv[i], "-ts") == 0)
+ { // time separator, next arg should be a seconds (1-3600)
+ if (time_spec)
+ { if (line)
+ fprintf(stderr,
+ "-tm, -ts, are mutually exclusive, in <%s> at line %d\n",
+ f_name, line);
+ else
+ fprintf(stderr, "-tm, -ts, are mutually exclusive\n");
+ return(-1);
+ }
+
+ if (((i+1) < argc) && (atoi(argv[i+1]) >= 1) && (atoi(argv[i+1]) <= 3600))
+ { i++;
+ time_spec = 1;
+ // arg OK, do nothing
+ }
+ else
+ { if (line)
+ fprintf(stderr,
+ "-ts: Invalid argument (1-3600 seconds) in <%s> at line %d\n",
+ f_name, line);
+ else
+ fprintf(stderr, "-ts: Invalid argument (1-3600 seconds)\n");
+ return(-1);
+ }
+ }
+ else if (strcmp(argv[i], "-n") == 0)
+ { // nr of data pump, before stop collection,
+ // next arg should be a int > 0
+ if (((i+1) < argc) && (atoi(argv[i+1]) >= 1) && (atoi(argv[i+1]) <= 99999))
+ { i++;
+ // arg OK, do nothing
+ }
+ else
+ { if (line)
+ fprintf(stderr,
+ "-n: Invalid argument (1-99999 times) in <%s> at line %d\n",
+ f_name, line);
+ else
+ fprintf(stderr, "-n: Invalid argument (1-99999 times)\n");
+ return(-1);
+ }
+ }
+ else if (strcmp(argv[i], "-h") == 0)
+ { // we do NOT want header (default with header)
+ // arg OK, do nothing
+ }
+ else if (strcmp(argv[i], "-S") == 0)
+ { // we have used use specs from a file instead of standard info,
+ // next arg is an existing readable filename
+ // as already parsed correctly, we skip here.
+ i++;
+ }
+ else if (strcmp(argv[i], "-I") == 0)
+ { // we have used input from a file instead of command line
+ // next arg is an existing readable filename
+ // as already parsed correctly, we skip here.
+ i++;
+ }
+ else
+ {
+ if (line)
+ fprintf(stderr, "Unrecognized option %s in <%s> at line %d\n",
+ argv[i], f_name, line);
+ else
+ fprintf(stderr, "Unrecognized option %s\n", argv[i]);
+ return(-1);
+ }
+ }
+ else
+ { // should be required data
+ tmp = strdup(argv[i]);
+ p = strtok(tmp, ":\t\n");
+ while (p != NULL)
+ {
+ // check if there is an output format specification
+ o = p;
+ while (*o)
+ {
+ o++;
+ if (*o == '-')
+ { *o = '\0';
+ o++;
+ if (strlen(o) == 0)
+ {
+ // we have 'minus', so, probably forget format ...
+
+ if (line)
+ fprintf(stderr,
+ "Required data <%s->, without format specifiers in <%s> at line %d\n",
+ p, f_name, line);
+ else
+ fprintf(stderr,
+ "Required data <%s->, without format specifiers\n", p);
+ return(-1);
+ }
+ }
+ }
+
+ // we check for params
+ found_data = 0;
+ info = start;
+ while (info->next != NULL)
+ {
+ info = info->next;
+ if (strcmp(p, info->name) == 0)
+ {
+ if (ctr > NM_MAX_FIELDS)
+ {
+ if (line)
+ fprintf(stderr,
+ "too much data field ... in file <%s> at line %d\n",
+ f_name, line);
+ else
+ fprintf(stderr, "too much data field ...\n");
+ return (-1);
+ }
+/*
+ data[ctr] = info;
+ out_f[ctr] = *o;
+*/
+ found_data = 1;
+ ctr++;
+ break;
+ }
+ }
+
+ if (found_data == 0)
+ {
+ if (line)
+ fprintf(stderr,
+ "Required data <%s>, not found in info-mon specifications in <%s> at line %d\n",
+ p, f_name, line);
+ else
+ fprintf(stderr,
+ "Required data <%s>, not found in info-mon specifications\n", p);
+ return(-1);
+ }
+
+ p = strtok(NULL, ":\t\n");
+
+ } // end while strtok
+
+ } // end else '-' (short options)
+
+ i++;
+
+ } // end while
+
+ if (ctr == 0)
+ {
+ if (line)
+ fprintf(stderr, "no required data! in <%s> at line %d\n", f_name, line);
+ else
+ fprintf(stderr, "no required data!\n");
+ return(-1);
+ }
+
+ return 0;
+}
+
+// 2, parse the arguments and process the command line
+// no checks are needed here, because already do in parse_check
+// it return a pointer to info needed for make output, or NULL if errors
+///////////////////////////////////////////////////////////////////////////////
+OUT_INFO_MON *parse_process(int argc, char *argv[], PARAM_INFO_MON *start)
+{
+ int ctr;
+ int i;
+ int time_spec;
+ int found_data;
+ int req_tm;
+ int req_ts;
+ char *p;
+ char *tmp;
+ char *o;
+ PARAM_INFO_MON *info; // iterator on this list
+ OUT_INFO_MON *out_param; // iterator on this list
+
+ if ((out_param = malloc(sizeof(OUT_INFO_MON))) == NULL)
+ { fprintf(stderr, "no mem\n");
+ return(NULL);
+ }
+
+#ifdef DEBUG
+ fprintf(stderr, "parse_process: argc = %d\n", argc);
+ for (i = 0; i < argc; i++)
+ fprintf(stderr, "argv[%d] = <%s>\n",i, argv[i]);
+#endif
+
+ for (i = 0; i < NM_MAX_FIELDS; i++)
+ out_param->data[i] = NULL;
+
+ strcpy(out_param->req_fs, " ");
+#ifdef WIN32
+ strcpy(out_param->req_ls, "\n\r");
+#else
+ strcpy(out_param->req_ls, "\n");
+#endif
+ time_spec = 0;
+ out_param->req_n = 0;
+ out_param->req_header = 1;
+
+ time_spec = 0;
+ req_tm = 200; /* default wait */
+ req_ts = 0;
+
+ ctr = 0;
+ i = 0;
+ while (i < argc)
+ {
+ p = argv[i];
+ if (*p == '-')
+ { // should be one of the short option
+ if (strcmp(argv[i], "-fs") == 0)
+ { // field separator, next arg should be a string
+ if (((i+1) < argc) && (strlen(argv[i+1]) < 10))
+ { i++;
+ strcpy(out_param->req_fs, argv[i]);
+ }
+ else
+ { fprintf(stderr, "NEVER BE:-fs: Invalid field separator\n");
+ return(NULL);
+ }
+ }
+ else if (strcmp(argv[i], "-ls") == 0)
+ { // line separator, next arg should be a string
+ if (((i+1) < argc) && (strlen(argv[i+1]) < 10))
+ { i++;
+ strcpy(out_param->req_ls, argv[i]);
+ }
+ else
+ { fprintf(stderr, "NEVER BE:-ls: Invalid line separator\n");
+ return(NULL);
+ }
+ }
+ else if (strcmp(argv[i], "-tm") == 0)
+ { // time separator, next arg should be a millisecond (200-10000)
+ if (time_spec)
+ { fprintf(stderr, "NEVER BE:-tm, -ts, are mutually exclusive");
+ return(NULL);
+ }
+
+ if (((i+1) < argc) && (atoi(argv[i+1]) >= 200) && (atoi(argv[i+1]) <= 10000))
+ { i++;
+ req_tm = atoi(argv[i]);
+ time_spec = 1;
+ }
+ else
+ { fprintf(stderr, "NEVER BE:-tm: Invalid argument (200-10000 milliseconds)\n");
+ return(NULL);
+ }
+ }
+ else if (strcmp(argv[i], "-ts") == 0)
+ { // time separator, next arg should be a seconds (1-3600)
+ if (time_spec)
+ { fprintf(stderr, "NEVER BE:-tm, -ts, are mutually exclusive");
+ return(NULL);
+ }
+
+ if (((i+1) < argc) && (atoi(argv[i+1]) >= 1) && (atoi(argv[i+1]) <= 3600))
+ { i++;
+ req_ts = atoi(argv[i]);
+ time_spec = 1;
+
+ // delete default
+ req_tm = 0;
+ }
+ else
+ { fprintf(stderr, "NEVER BE:-ts: Invalid argument (1-3600 seconds)\n");
+ return(NULL);
+ }
+ }
+ else if (strcmp(argv[i], "-n") == 0)
+ { // nr of data pump, before stop collection,
+ // next arg should be a int > 0
+ if (((i+1) < argc) && (atoi(argv[i+1]) >= 1) && (atoi(argv[i+1]) <= 99999))
+ { i++;
+ out_param->req_n = atoi(argv[i]);
+ }
+ else
+ { fprintf(stderr, "NEVER BE:-n: Invalid argument (1-99999 times)\n");
+ return(NULL);
+ }
+ }
+ else if (strcmp(argv[i], "-h") == 0)
+ { // we do NOT want header (default with header)
+ out_param->req_header = 0;
+ }
+ else if (strcmp(argv[i], "-S") == 0)
+ { // we have used use specs from a file instead of standard info,
+ // next arg is an existing readable filename
+ // as already parsed correctly, we skip here.
+ i++;
+ }
+ else if (strcmp(argv[i], "-I") == 0)
+ { // we have used input from a file instead of command line
+ // next arg is an existing readable filename
+ // as already parsed correctly, we skip here.
+ i++;
+ }
+ else
+ {
+ fprintf(stderr, "NEVER BE:Unrecognized option %s\n", argv[i]);
+ return(NULL);
+ }
+ }
+ else
+ { // should be required data
+ tmp = strdup(argv[i]);
+ p = strtok(tmp, ":\t\n");
+ while (p != NULL)
+ {
+ // check if there is an output format specification
+ o = p;
+ while (*o)
+ {
+ o++;
+ if (*o == '-')
+ { *o = '\0';
+ o++;
+ if (strlen(o) == 0)
+ {
+ // we have 'minus', so, probably forget format ...
+
+ fprintf(stderr,
+ "NEVER BE:Required data <%s->, without format specifiers\n", p);
+ return(NULL);
+ }
+ }
+ }
+
+ // we check for params
+ found_data = 0;
+ info = start;
+ while (info->next != NULL)
+ {
+ info = info->next;
+ if (strcmp(p, info->name) == 0)
+ {
+ if (ctr > NM_MAX_FIELDS)
+ {
+ fprintf(stderr, "NEVER BE:too much data field ...");
+ return(NULL);
+ }
+ out_param->data[ctr] = info;
+ out_param->out_f[ctr] = *o;
+ found_data = 1;
+ ctr++;
+ break;
+ }
+ }
+
+ if (found_data == 0)
+ {
+ fprintf(stderr,
+ "NEVER BE:Required data <%s>, not found in info-mon specifications\n", p);
+ return(NULL);
+ }
+
+
+ p = strtok(NULL, ":\t\n");
+
+ } // end while strtok
+
+ // here, we have an array of pointers to required data
+ // and an array of output specifiers, from 0 to [ctr-1]
+
+ } // end else '-' (short options)
+
+ i++;
+
+ } // end while
+
+ if (ctr == 0)
+ {
+ fprintf(stderr, "NEVER BE:no required data!\n");
+ return(NULL);
+ }
+
+ // now, what netmon screen we need to retrieve ?
+ // we need somewhat were checking is faster, as our goal is lower cicle time
+
+ // we can have NM_MAX_SCREEN=254 screens, so we use an array, of unsigned char,
+ // each char contain number of needed screen, 255 is list terminator
+
+ for (i = 0; i <= NM_MAX_SCREEN; i++)
+ out_param->req_screen[i] = 255;
+
+ ctr = 0;
+#ifdef DEBUG
+fprintf(stderr, "Start Required data %s screen %d\n", out_param->data[ctr]->name, out_param->data[ctr]->s_nr);
+#endif
+ while (out_param->data[ctr] != NULL)
+ {
+#ifdef DEBUG
+fprintf(stderr, "Required data %s screen %d\n", out_param->data[ctr]->name, out_param->data[ctr]->s_nr);
+#endif
+ // check if screen already in
+ found_data = 0;
+ i = 0;
+ while (out_param->req_screen[i] != 255)
+ {
+ if (out_param->req_screen[i] == out_param->data[ctr]->s_nr)
+ { // already load, skip
+ found_data = 1;
+ break;
+ }
+ i++;
+ }
+
+ if (found_data == 0)
+ {
+#ifdef DEBUG
+fprintf(stderr, "i = %d, out_param->req_screen[%d] = %d\n", i, i, out_param->data[ctr]->s_nr);
+#endif
+ out_param->req_screen[i] = out_param->data[ctr]->s_nr;
+ i++;
+ }
+
+ ctr++;
+ }
+
+#ifdef DEBUG
+i = 0;
+while (out_param->req_screen[i] != 255)
+{
+ fprintf(stderr, "Required screen %d\n", out_param->req_screen[i]);
+ i++;