diff options
Diffstat (limited to 'device-functions.c')
-rw-r--r-- | device-functions.c | 386 |
1 files changed, 230 insertions, 156 deletions
diff --git a/device-functions.c b/device-functions.c index 0e5338a..f3c06d3 100644 --- a/device-functions.c +++ b/device-functions.c @@ -1,5 +1,4 @@ #include "device-functions.h" -#include "dummy_functions.h" #include "globals.h" #include "version.h" #include "error_utils.h" @@ -10,11 +9,19 @@ #include "menus.h" #include <math.h> #include <glib.h> +#include <libuser/user.h> +#include <libuser/config.h> +#include <security/pam_appl.h> +#include <security/pam_misc.h> + + +static void start_gate_override (); +static void stop_gate_override (); void idn_string(gchar** response) { - *response = g_strdup_printf ("AVTECH ELECTROSYSTEMS,%s,%s,v%s", + *response = g_strdup_printf ("AVTECH ELECTROSYSTEMS,%s,SN:%s,v%s", globals.Flash.model_num, globals.Flash.serial_num, FW_VERSION); @@ -118,7 +125,6 @@ void Main_Rst (void) // establishes min/max values for queries, but reports no errors Error_check(globals.ChannelState); - globals.Changes.update_whole_main_menu=YES; Ctrl_PRF_Limiter(1); @@ -132,7 +138,7 @@ void Main_Rst (void) } -int set_dac(int dac, int word) +void set_dac(int dac, int word) { /* allows dacs to be disabled (using dac=-1, for example) */ if ((dac >= 0) && (dac < 8)) { @@ -389,6 +395,10 @@ int Set_Pw(int check_possible_only,int word_override,int range_override,int chan /* AVPP-style: lower PW range is voltage-controlled */ if (globals.Flash.volt_ctrl_pw[channel]) { + + // reset PG B line (see below) + globals.Registers.shift_reg_out[2] &= (long)0x7ffff; + /* use DAC8420 to control PW in lowest PW range */ if (!relay_range) { set_dac(globals.Flash.pw_dac[channel],word_out); @@ -407,6 +417,9 @@ int Set_Pw(int check_possible_only,int word_override,int range_override,int chan if (relay_range==1) { cap_range_control=0; + // set XTRA RLY 5 high in this range for AVR-E3-B-R5-N-M5, and other + // units with PG A, B, and C. This corresponds to PG B. + globals.Registers.shift_reg_out[2] |= (long)0x80000; } else { cap_range_control = 1 << (relay_range-2); } @@ -444,10 +457,6 @@ int Set_Pw(int check_possible_only,int word_override,int range_override,int chan set_dac(globals.Flash.monocycle_dac[0],word_out); } - if (set_pw!=globals.ChannelState[channel].pw) { - globals.Changes.update_pw=YES; - } - globals.ChannelState[channel].pw=set_pw; Set_Update_Chans(); @@ -628,10 +637,6 @@ int Set_frequency(int check_possible_only,int word_override,int range_override,i globals.Registers.shift_reg_out[2] = ((long)(globals.Registers.shift_reg_out[2] & 0xfff00)) | ((long)cap_range_control); /* bottom 8 bits of 20 bits */ } - if (set_freq!=globals.ChannelState[channel].frequency) { - globals.Changes.update_freq=YES; - } - g_print_debug("freq range %d, word %d\n",relay_range,word_out); globals.ChannelState[channel].frequency=set_freq; @@ -726,10 +731,6 @@ int Set_Delay(int check_possible_only,int word_override,int range_override,int c control_pcb107(Second_Dly_Port,globals.Flash.delay_dac[channel],word_out,relay_range); } - if (set_delay!=globals.ChannelState[channel].delay) { - globals.Changes.update_delay=YES; - } - globals.ChannelState[channel].delay=set_delay; Set_Update_Chans(); @@ -756,13 +757,11 @@ int Set_Double(int channel,int new_setting) } if (new_setting == double_off) { - globals.Registers.shift_reg_out[0] &= 0xdf; /* turn double-pulse off */ + globals.Registers.shift_reg_out[0] &= 0xdf; // turn double-pulse off + Ctrl_PRF_Limiter (1); // normal prf limiting } else { - globals.Registers.shift_reg_out[0] |= 0x20; /* turn double-pulse on */ - } - - if (globals.ChannelState[channel].double_pulse!=new_setting) { - globals.Changes.update_delay=YES; + globals.Registers.shift_reg_out[0] |= 0x20; // turn double-pulse on + Ctrl_PRF_Limiter (0); // disable prf limiter } globals.ChannelState[channel].double_pulse=new_setting; @@ -786,7 +785,7 @@ void Ctrl_PRF_Limiter(int enable) } -int Set_Mux(int channel) +void Set_Mux(int channel) { int mux_out; @@ -849,8 +848,6 @@ int Set_Func(int channel,int mode) globals.Registers.shift_reg_out[2] = ((long) (globals.Registers.shift_reg_out[2] & 0xbffff)) | (long) (((long) (mode & 0x08)) << (globals.Flash.ext_amplify_xtra_rly[channel]+11)); - - globals.Changes.update_func=YES; } @@ -892,10 +889,6 @@ int Set_Pol(int channel,int mode) return error_num; } - if (globals.ChannelState[channel].polarity!=mode) { - globals.Changes.update_inv=YES; - } - globals.ChannelState[channel].polarity=mode; Set_Mux(channel); @@ -912,10 +905,6 @@ int Set_Hold(int channel,int mode) return InvalidChannel; } - if (globals.ChannelState[channel].hold_setting!=mode) { - globals.Changes.update_pw=YES; - } - globals.ChannelState[channel].hold_setting=mode; Set_Update_Chans(); @@ -956,6 +945,9 @@ int Set_Output_State(int channel,int mode) bus_setpin(OUTPUT_RELAY, 1); /* turn output on */ bus_setpin(PW_ENABLE, 1); /* enable PW circuit */ + + g_usleep (800e3); /* wait for extended-off circuit to work */ + globals.Timers.last_activity_at[channel] = sec_timer(); } else { bus_setpin(PW_ENABLE, 0); /* disable PW circuit */ @@ -963,10 +955,6 @@ int Set_Output_State(int channel,int mode) globals.Timers.last_activity_at[channel] = 0L; } - if (globals.ChannelState[channel].output_state!=mode) { - globals.Changes.update_output=YES; - } - globals.ChannelState[channel].output_state=mode; Set_Update_Chans(); @@ -1018,8 +1006,6 @@ int Set_Trig_Source(int channel,int mode) Set_frequency(0,0,0,channel,use_freq); Set_Pwmode(channel,use_ab_mode); } - - globals.Changes.update_freq=YES; } globals.ChannelState[channel].trigger_source=mode; @@ -1031,34 +1017,23 @@ int Set_Trig_Source(int channel,int mode) mode=source_external; } - + gate_mode = 0; if (mode==source_internal) { - gate_mode=0; /* frequency is automatically lowered if pw or delay have been changed to conflicting */ /* settings while in a non-internal mode */ globals.Registers.shift_reg_out[0] = (globals.Registers.shift_reg_out[0] & 0xe3) | 0; } else if (mode==source_external) { - gate_mode=0; globals.ChannelState[channel].hold_setting=hold_width; globals.Registers.shift_reg_out[0] = (globals.Registers.shift_reg_out[0] & 0xe3) | 3<<2; } else if (mode==source_manual) { - gate_mode=0; globals.ChannelState[channel].hold_setting=hold_width; globals.Registers.shift_reg_out[0] = (globals.Registers.shift_reg_out[0] & 0xe3) | 1<<2; } else if (mode==source_hold) { gate_mode=1; } else if (mode==source_immediate) { - if (gate_mode==1) { - globals.Registers.shift_reg_out[0] = (globals.Registers.shift_reg_out[0] & 0xe3) | 4<<2; - Main_update_shift_registers(); - gate_mode=0; /* allow triggering */ - bus_setpin(O_GATE, gate_mode); - globals.Registers.shift_reg_out[0] = (globals.Registers.shift_reg_out[0] & 0xe3) | 7<<2; - } else { - globals.Registers.shift_reg_out[0] = (globals.Registers.shift_reg_out[0] & 0xe3) | 4<<2; - Main_update_shift_registers(); - globals.Registers.shift_reg_out[0] = (globals.Registers.shift_reg_out[0] & 0xe3) | 7<<2; - } + globals.Registers.shift_reg_out[0] = (globals.Registers.shift_reg_out[0] & 0xe3) | 4<<2; + Main_update_shift_registers(); + globals.Registers.shift_reg_out[0] = (globals.Registers.shift_reg_out[0] & 0xe3) | 7<<2; } Main_update_shift_registers(); @@ -1081,10 +1056,6 @@ int Set_Gate_Sync(int channel,int mode) globals.Registers.shift_reg_out[0] = (globals.Registers.shift_reg_out[0] & 0xfe) | 1; } - if (globals.ChannelState[channel].gate_type!=mode) { - globals.Changes.update_gate=YES; - } - globals.ChannelState[channel].gate_type=mode; Set_Update_Chans(); @@ -1105,10 +1076,6 @@ int Set_Gate_Level(int channel,int mode) globals.Registers.shift_reg_out[0] = (globals.Registers.shift_reg_out[0] & 0xfd) | 0; } - if (globals.ChannelState[channel].gate_level!=mode) { - globals.Changes.update_gate=YES; - } - globals.ChannelState[channel].gate_level=mode; Set_Update_Chans(); @@ -1116,7 +1083,7 @@ int Set_Gate_Level(int channel,int mode) } -int start_gate_override () +static void start_gate_override () { /* just set gate bit high, if not already high */ int i; @@ -1127,7 +1094,7 @@ int start_gate_override () } -int stop_gate_override () +static void stop_gate_override () { /* release gate (if not in hold mode) */ int i; @@ -1351,10 +1318,6 @@ int Set_Pwmode(int channel,int mode) return AB_Mode_Error; } - if (globals.ChannelState[channel].ab_mode!=mode) { - globals.Changes.update_pw=YES; - } - globals.ChannelState[channel].ab_mode=mode; Set_Mux(0); @@ -1566,11 +1529,6 @@ int Set_Logic_Level(int channel,int mode) } } - - if (globals.ChannelState[channel].logic_level!=mode) { - globals.Changes.update_logic_level=YES; - } - globals.ChannelState[channel].logic_level=mode; Set_Update_Chans(); @@ -1689,7 +1647,6 @@ int Set_Route(int channel, int module, int mode) } if (mode!=globals.ChannelState[channel].route_primary) { - globals.Changes.update_routes=YES; globals.ChannelState[channel].route_primary=mode; } } @@ -1701,7 +1658,6 @@ int Set_Route(int channel, int module, int mode) } if (mode!=globals.ChannelState[channel].route_secondary) { - globals.Changes.update_routes=YES; globals.ChannelState[channel].route_secondary=mode; } } @@ -1796,7 +1752,7 @@ int Set_Dly_Shr_Nom(int channel,int calibration_point_number) Main_update_shift_registers(); - Menu_Update_Display(); + Show_Main_Menu(); return OK; } @@ -2055,7 +2011,7 @@ int Set_Cal_Nom(int channel,int calibration_point_number,int parameter, float *n Set_Mux(true_channel); Main_update_shift_registers(); - Menu_Update_Display(); + Show_Main_Menu(); /* re-enable error-checking */ globals.Flash.fully_programmed=All_Programmed; @@ -2234,7 +2190,7 @@ int Set_VI_Cal_Pnt(int parameter,int channel,int calibration_point_number,float Set_Cal_Nom(channel,calibration_point_number,parameter,NULL); Main_update_shift_registers(); - Menu_Update_Display(); + Show_Main_Menu(); eprom_loc = (char *) (&pwl_amp[index]) - (char *) &(globals.Flash.flash_start); writeUserBlock(&globals.Flash, eprom_loc, sizeof(nom_ampl)); @@ -2397,7 +2353,7 @@ int Set_VI_Del_Cal(int parameter,int channel,int calibration_point_number) Set_Offset(0,0,0,0,channel,0.0); Main_update_shift_registers(); - Menu_Update_Display(); + Show_Main_Menu(); eprom_loc = (char *) pointer_short1 - (char *) &(globals.Flash.flash_start); writeUserBlock(&globals.Flash, eprom_loc, size_of_short1); @@ -2500,6 +2456,32 @@ int Set_VI_Control(int parameter,int channel,float new_ampl,int *point_found,int top_range_only=1; } + if (globals.Flash.couple_first_N_pw_ranges_to_ampl_ranges[channel]) { + int curr_pw_range = 0; + int parse_sr = globals.Registers.shift_reg_out[3] & 0x7f; + + while (parse_sr) { + ++curr_pw_range; + parse_sr = parse_sr >> 1; + } + + if (globals.Flash.volt_ctrl_pw[channel]) { + // ranges are shifted in these units + ++curr_pw_range; + // except for minimum range + if (globals.Registers.shift_reg_out[3] & (long)0x01000) { + curr_pw_range = 0; + } + } + + starting_range = curr_pw_range; + if (starting_range > globals.Flash.couple_first_N_pw_ranges_to_ampl_ranges[channel]) { + starting_range = globals.Flash.couple_first_N_pw_ranges_to_ampl_ranges[channel]; + } + + top_range_only = 0; + } + break; case pwl_os_values: decreasing_values_allowed=YES; /* allows Vc=0 to corresponds to most + OS, and Vc=10V to give most - OS */ @@ -3366,11 +3348,6 @@ int Set_Burst_Count(int channel,int count,float new_burst_time) return check_valid; } - /* update variables if OK */ - if (count!=globals.ChannelState[channel].burst_count) { - globals.Changes.update_burst_count=YES; - } - globals.ChannelState[channel].burst_count = count; Set_Update_Chans(); @@ -3496,11 +3473,6 @@ int Set_Burst_Time(int check_possible_only,int word_override,int range_override, globals.Registers.last_relay_driver_settings[2] = relay_range; - /* update variables if OK */ - if (new_burst_time!=globals.ChannelState[channel].burst_time) { - globals.Changes.update_burst_time=YES; - } - globals.ChannelState[channel].burst_time = new_burst_time; Set_Update_Chans(); @@ -3631,11 +3603,6 @@ int Set_rise_time(int check_possible_only,int word_override,int range_override,i } } - /* update variables if OK */ - if (new_rise_time!=globals.ChannelState[channel].rise_time) { - globals.Changes.update_rise_time=YES; - } - globals.ChannelState[channel].rise_time = new_rise_time; globals.Registers.last_rise_time_relay_setting = range_control; @@ -3683,11 +3650,6 @@ int Set_current_limit(int check_possible_only,int channel,float new_adj_current_ word_out = (int) ( ((float) dac_max) * (limit/globals.Flash.current_limit_full_scale[channel]) ); set_dac(globals.Flash.current_limit_dac[channel],word_out); - /* update variables if OK */ - if (limit!=globals.ChannelState[channel].soft_current_limit) { - globals.Changes.update_soft_current_limit=YES; - } - globals.ChannelState[channel].soft_current_limit=limit; return OK; @@ -3837,11 +3799,6 @@ int Set_slew(int check_possible_only,int word_override,int range_override,int ch I2C_Write(PCF8574,range_control); - /* update variables if OK */ - if (new_slew!=globals.ChannelState[channel].slew) { - globals.Changes.update_slew=YES; - } - globals.ChannelState[channel].slew = new_slew; Set_Update_Chans(); @@ -4023,8 +3980,9 @@ int go_cal(CalStruct *caldata) int i, status, points; float meas, nom_val, change; float min_val, max_val, chk_val; - char lcd_msg[LCD_cols+1]; - char prefix[LCD_cols+1]; + + gchar *lcd_msg = NULL; + gchar *prefix = NULL; points = Get_VI_Num_Pnts(caldata->cal_type,caldata->channel); @@ -4059,14 +4017,16 @@ int go_cal(CalStruct *caldata) LCD_write(0,0,"Self-calibration in progress."); if (caldata->cal_type == pwl_period_values) { - sprintf (prefix, "CH%d PER %d:",caldata->channel+1,i); + prefix = g_strdup_printf ("CH%d PER %d:",caldata->channel+1,i); } else if (caldata->cal_type == pwl_pw_values) { - sprintf (prefix, "CH%d PW %d:",caldata->channel+1,i); + prefix = g_strdup_printf ("CH%d PW %d:",caldata->channel+1,i); } else if (caldata->cal_type == pwl_delay_values) { - sprintf (prefix, "CH%d DLY %d:",caldata->channel+1,i); + prefix = g_strdup_printf ("CH%d DLY %d:",caldata->channel+1,i); } - sprintf (lcd_msg, "%s %.3e",prefix,nom_val); + + lcd_msg = g_strdup_printf ("%s %.3e",prefix,nom_val); LCD_write(2,0,lcd_msg); + g_free (lcd_msg); if (caldata->cal_type == pwl_period_values) { I2C_Self_Cal (caldata->channel, MEAS_PRF, &meas, 1.0 / globals.ChannelState[caldata->channel].frequency); @@ -4090,10 +4050,17 @@ int go_cal(CalStruct *caldata) LCD_clear(); LCD_write(0,0,"Self-calibration in progress."); - sprintf (lcd_msg, "%s %.3e -> %.3e",prefix,nom_val,meas); + + lcd_msg = g_strdup_printf ("%s %.3e -> %.3e",prefix,nom_val,meas); LCD_write(2,0,lcd_msg); - sprintf (lcd_msg, "changed %6.2f%%, err: %d",change,status); + g_free (lcd_msg); + + lcd_msg = g_strdup_printf ("changed %6.2f%%, err: %d",change,status); LCD_write(3,0,lcd_msg); + g_free (lcd_msg); + + g_free (prefix); + g_usleep (2e6); } } @@ -4102,44 +4069,52 @@ int go_cal(CalStruct *caldata) } -int cal_string(char *parameter, CalStruct *caldata) +void cal_string(char *parameter, CalStruct *caldata) { - char string[max_output_length]; - - sprintf(string,"CH%d %s cal: %d errors. Adj: %6.2f%% max, %6.2f%% avg.\n\r", caldata->channel+1,parameter, caldata->error, caldata->max_change, caldata->avg_change); - strcat (caldata->response, string); + gchar *string = g_strdup_printf ("CH%d %s cal: %d errors. Adj: %6.2f%% max, %6.2f%% avg.\r\n", caldata->channel+1,parameter, caldata->error, caldata->max_change, caldata->avg_change); + g_string_append (caldata->response, string); + g_free (string); } int self_cal() { CalStruct caldata; - return do_full_self_cal(&caldata); + + int status = do_full_self_cal(&caldata); + + g_string_free (caldata.response, TRUE); + + return status; } int do_full_self_cal(CalStruct *caldata) { - char string[LCD_cols+1]; + gchar *string; long start_timer, diff_timer; int eprom_loc; + caldata->response = g_string_new (""); + Menu_Clear_Buttons(); LCD_clear(); /*0123456789012345678901234567890123456789*/ LCD_write(0,0,"Self-calibration in progress."); /*0123456789012345678901234567890123456789*/ - sprintf(string,"Typical run time: %d min, %d sec.", globals.Flash.self_cal_typical_time_min, globals.Flash.self_cal_typical_time_sec); + + string = g_strdup_printf ("Typical run time: %d min, %d sec.", globals.Flash.self_cal_typical_time_min, globals.Flash.self_cal_typical_time_sec); LCD_write(1,0,string); + g_free (string); while ((sec_timer() - globals.Timers.startup_timer_value) < (long)globals.Flash.self_cal_pause) { /*0123456789012345678901234567890123456789*/ - sprintf (string, "Min warm-up is %ds, on for %lds.", globals.Flash.self_cal_pause, sec_timer() - globals.Timers.startup_timer_value); + string = g_strdup_printf ("Min warm-up is %ds, on for %lds.", globals.Flash.self_cal_pause, sec_timer() - globals.Timers.startup_timer_value); LCD_write(3,0,string); + g_free (string); g_usleep (2e5); } start_timer = sec_timer(); - caldata->response[0] = 0; caldata->total_errors = 0; caldata->total_max_change = 0.0; @@ -4177,21 +4152,24 @@ int do_full_self_cal(CalStruct *caldata) LCD_clear(); /*0123456789012345678901234567890123456789*/ LCD_write(0,0,"Self-calibration complete."); - sprintf (string, "%d errors. Max change: %6.2f%%", caldata->total_errors, caldata->total_max_change); + + string = g_strdup_printf ("%d errors. Max change: %6.2f%%", caldata->total_errors, caldata->total_max_change); LCD_write(1,0,string); + g_free (string); + LCD_write(2,0,"More details are provided by \"cal?\""); g_usleep (3e6); - Menu_Update_Display(); + Show_Main_Menu(); diff_timer = sec_timer() - start_timer; globals.Flash.self_cal_typical_time_min = (int) (diff_timer / 60); globals.Flash.self_cal_typical_time_sec = (int) (diff_timer % 60); - // FIXME - cpp buffer error - sprintf(string,"Completed in %d minutes and %d seconds\n\r", globals.Flash.self_cal_typical_time_min, globals.Flash.self_cal_typical_time_sec); - strcat (caldata->response, string); + string = g_strdup_printf ("Completed in %d minutes and %d seconds\r\n", globals.Flash.self_cal_typical_time_min, globals.Flash.self_cal_typical_time_sec); + g_string_append (caldata->response, string); + g_free (string); eprom_loc = (char *) &(globals.Flash.self_cal_typical_time_min) - (char *) &(globals.Flash.flash_start); writeUserBlock(&globals.Flash, eprom_loc, sizeof(globals.Flash.self_cal_typical_time_min)); @@ -4200,9 +4178,12 @@ int do_full_self_cal(CalStruct *caldata) if (caldata->total_errors) { return SelfCalError; + } else { + return OK; } } + int I2C_Self_Cal(int channel, int meas_mode, float *meas, float target_time) { #define MAX_TRIES 35 @@ -4451,7 +4432,6 @@ void Set_Rcl(int setting_num) Menu_Clear_Buttons(); globals.Flags.do_check_settings=YES; /* check for conflicting settings */ - globals.Changes.update_whole_main_menu=YES; Error_check(globals.ChannelState); /* establishes min/max values for queries, but reports no errors */ @@ -4538,6 +4518,9 @@ void Set_Sav(int setting_num) void Main_update_shift_registers() { + static GStaticMutex mutex = G_STATIC_MUTEX_INIT; + g_static_mutex_lock (&mutex); + /* send MSB first, LSB last */ /* send highest # SR first */ @@ -4619,40 +4602,131 @@ void Main_update_shift_registers() /* save relay data for comparision next time */ globals.Registers.last_relay_driver_settings[0]=globals.Registers.shift_reg_out[2]; globals.Registers.last_relay_driver_settings[1]=globals.Registers.shift_reg_out[3]; + + // reset update sensors + globals.Changes.update_os = 0; + globals.Changes.update_amp = 0; + globals.Changes.update_zout = 0; + globals.Changes.update_load = 0; + + g_static_mutex_unlock (&mutex); +} + + +int IO_Setup_RS232(int baud, char hardhand, gboolean update_flash) +{ + FILE* configfile = fopen("/tmp/instgettyopts", "w"); + if(configfile) { + fprintf(configfile, "OPTS=-L %s\n", hardhand ? "-h" : ""); + fprintf(configfile, "BAUD=%d\n", baud); + fclose(configfile); + system("systemctl --no-block restart inst-getty@ttyO5.service"); + } + + globals.Flash.baud = baud; + globals.Flash.hardhand = hardhand; + + if (update_flash) { + int size = sizeof(globals.Flash.baud) + sizeof(globals.Flash.parity) + sizeof(globals.Flash.stopbits) + + sizeof(globals.Flash.databits) + sizeof(globals.Flash.hardhand) + sizeof(globals.Flash.echo); + + int eprom_loc = (char *) &(globals.Flash.baud) - (char *) &(globals.Flash.flash_start); + writeUserBlock(&globals.Flash, eprom_loc, size); + } + return OK; +} + +// this is a conversation handler for pam, it basically sends the password when pam asks for it + +static int conversation(int num_msg, const struct pam_message **msgs, struct pam_response **resp, void *appdata_ptr) +{ + + struct pam_response* responses = calloc(num_msg, sizeof(struct pam_response)); + if (!responses) { + return PAM_CONV_ERR; + } + + int i; // not compiling in gnu99 mode? + for (i = 0; i < num_msg; i++) { + const struct pam_message *msg = msgs[i]; + struct pam_response* response = &(responses[i]); + switch (msg->msg_style) { + case PAM_PROMPT_ECHO_OFF: + response->resp = strdup((char*) appdata_ptr); + if (!response->resp) { + return PAM_CONV_ERR; + } + break; + + default: + return PAM_CONV_ERR; + } + response->resp_retcode = 0; + } + + *resp = responses; + + return PAM_SUCCESS; } +static gboolean checkpassword(const char* username, char* password) +{ + struct pam_conv pam_conversation = { conversation, password }; + pam_handle_t* pamh; + + if (pam_start("passwd", username, &pam_conversation, &pamh) != PAM_SUCCESS) { + return FALSE; + } + + if (pam_authenticate(pamh, 0) != PAM_SUCCESS) { + return FALSE; + } + + // we only want to check the password and not actually start a session, so get out of here + + pam_end(pamh, 0); + + return TRUE; +} -int IO_Setup_RS232(int baud, char parity, char stopbits, char databits, char hardhand, char echo, gboolean update_flash) +int change_password(gchar *old_password, gchar *new_password) { - // debugging - printf ("baud: %d, parity %d, stop bits %d, data bits %d, handshaking %d, echo %d\n\r", - baud, - parity, // 0 = none, 1 = odd, 2 = even - stopbits, - databits, - hardhand, // 0 = none, 1 = hard - echo); - - // FIXME implement serial port changes here - - if (1) { // FIXME if changes are successful - globals.Flash.baud = baud; - globals.Flash.parity = parity; - globals.Flash.stopbits = stopbits; - globals.Flash.databits = databits; - globals.Flash.hardhand = hardhand; - globals.Flash.echo = echo; - - if (update_flash) { - int size = sizeof(globals.Flash.baud) + sizeof(globals.Flash.parity) + sizeof(globals.Flash.stopbits) + - sizeof(globals.Flash.databits) + sizeof(globals.Flash.hardhand) + sizeof(globals.Flash.echo); - - int eprom_loc = (char *) &(globals.Flash.baud) - (char *) &(globals.Flash.flash_start); - writeUserBlock(&globals.Flash, eprom_loc, size); + + gboolean old_valid = TRUE; + + char* user = "admin"; + + // Skip password check if the supplied old_password is NULL. This + // only happens when resetting the password to the default. + if (old_password != NULL ) { + old_valid = checkpassword(user,old_password); + } + + if (old_valid == TRUE) { + struct lu_context *ctx; + struct lu_error *error = NULL; + struct lu_ent *ent; + + ctx = lu_start(user, lu_user, NULL, NULL, lu_prompt_console_quiet, NULL, &error); + + if (ctx == NULL ) { + return password_change_error; + } + + ent = lu_ent_new(); + + if (lu_user_lookup_name(ctx, user, ent, &error) == FALSE) { + return password_change_error; // user doesn't exist + } + + if (lu_user_setpass(ctx, ent, new_password, FALSE, &error) == FALSE) { + return password_change_error; } + + lu_end(ctx); + return OK; } else { - return HardwareError; + return password_change_error; } } - |