// Power Off the server in given slot static int server_power_off(uint8_t slot_id, bool gs_flag) { char vpath[64] = {0}; if (slot_id < 1 || slot_id > 4) { return -1; } sprintf(vpath, GPIO_VAL, gpio_power[slot_id]); if (write_device(vpath, "1")) { return -1; } sleep(1); if (write_device(vpath, "0")) { return -1; } if (gs_flag) { sleep(DELAY_GRACEFUL_SHUTDOWN); } else { sleep(DELAY_POWER_OFF); } if (write_device(vpath, "1")) { return -1; } return 0; }
/******************************************************************** * reset_06 WS2300 by sending command 06 (Linux version) * * Input: device number of the already open serial port * * Returns: nothing, exits progrsm if failing to reset * ********************************************************************/ void reset_06(WEATHERSTATION serdevice) { unsigned char command = 0x06; unsigned char answer; int i; for (i = 0; i < 100; i++) { // Discard any garbage in the input buffer tcflush(serdevice, TCIFLUSH); write_device(serdevice, &command, 1); // Occasionally 0, then 2 is returned. If zero comes back, continue // reading as this is more efficient than sending an out-of sync // reset and letting the data reads restore synchronization. // Occasionally, multiple 2's are returned. Read with a fast timeout // until all data is exhausted, if we got a two back at all, we // consider it a success while (1 == read_device(serdevice, &answer, 1)) { if (answer == 2) { return; } } usleep(50000 * i); //we sleep longer and longer for each retry } fprintf(stderr, "\nCould not reset\n"); exit(EXIT_FAILURE); }
int write_fan_led(const int fan, const char *color) { #if defined(CONFIG_WEDGE100) || defined(CONFIG_WEDGE) return write_device(fan_led[fan], color); #else return 0; #endif }
int server_shutdown(const char *why) { int fan; for (fan = 0; fan < total_fans; fan++) { write_fan_speed(fan + fan_offset, fan_max); } syslog(LOG_EMERG, "Shutting down: %s", why); write_device(GPIO_USERVER_POWER_DIRECTION, "out"); write_device(GPIO_USERVER_POWER, "0"); #ifdef CONFIG_WEDGE /* * Putting T2 in reset generates a non-maskable interrupt to uS, * the kernel running on uS might panic depending on its version. * sleep 5s here to make sure uS is completely down. */ sleep(5); if (write_device(GPIO_T2_POWER_DIRECTION, "out") || write_device(GPIO_T2_POWER, "1")) { /* * We're here because something has gone badly wrong. If we * didn't manage to shut down the T2, cut power to the whole box, * using the PMBus OPERATION register. This will require a power * cycle (removal of both power inputs) to recover. */ syslog(LOG_EMERG, "T2 power off failed; turning off via ADM1278"); system("rmmod adm1275"); system("i2cset -y 12 0x10 0x01 00"); } #else // TODO(7088822): try throttling, then shutting down server. syslog(LOG_EMERG, "Need to implement actual shutdown!\n"); #endif /* * We have to stop the watchdog, or the system will be automatically * rebooted some seconds after fand exits (and stops kicking the * watchdog). */ stop_watchdog(); sleep(2); exit(2); }
int write_fan_value(const int fan, const char *device, const int value) { char full_name[LARGEST_DEVICE_NAME]; char device_name[LARGEST_DEVICE_NAME]; char output_value[LARGEST_DEVICE_NAME]; snprintf(device_name, LARGEST_DEVICE_NAME, device, fan); snprintf(full_name, LARGEST_DEVICE_NAME, "%s/%s", PWM_DIR, device_name); snprintf(output_value, LARGEST_DEVICE_NAME, "%d", value); return write_device(full_name, output_value); }
// Update the USB Mux to the server at given slot int pal_switch_usb_mux(uint8_t slot) { char *gpio_sw0, *gpio_sw1; char path[64] = {0}; // Based on the USB mux table in Schematics switch(slot) { case 1: gpio_sw0 = "1"; gpio_sw1 = "0"; break; case 2: gpio_sw0 = "0"; gpio_sw1 = "0"; break; case 3: gpio_sw0 = "1"; gpio_sw1 = "1"; break; case 4: gpio_sw0 = "0"; gpio_sw1 = "1"; break; default: // Default is for BMC itself return 0; } sprintf(path, GPIO_VAL, GPIO_USB_SW0); if (write_device(path, gpio_sw0) < 0) { syslog(LOG_ALERT, "write_device failed for %s\n", path); return -1; } sprintf(path, GPIO_VAL, GPIO_USB_SW1); if (write_device(path, gpio_sw1) < 0) { syslog(LOG_ALERT, "write_device failed for %s\n", path); return -1; } return 0; }
// Power On the server in a given slot static int server_power_on(uint8_t slot_id) { char vpath[64] = {0}; sprintf(vpath, GPIO_VAL, gpio_power[slot_id]); if (write_device(vpath, "1")) { return -1; } if (write_device(vpath, "0")) { return -1; } sleep(1); if (write_device(vpath, "1")) { return -1; } return 0; }
int pm860x_page_reg_write(struct i2c_client *i2c, int reg, unsigned char data) { unsigned char zero; int ret; i2c_lock_adapter(i2c->adapter); read_device(i2c, 0xFA, 0, &zero); read_device(i2c, 0xFB, 0, &zero); read_device(i2c, 0xFF, 0, &zero); ret = write_device(i2c, reg, 1, &data); read_device(i2c, 0xFE, 0, &zero); read_device(i2c, 0xFC, 0, &zero); i2c_unlock_adapter(i2c->adapter); return ret; }
int pm860x_page_bulk_write(struct i2c_client *i2c, int reg, int count, unsigned char *buf) { unsigned char zero = 0; int ret; i2c_lock_adapter(i2c->adapter); read_device(i2c, 0xFA, 0, &zero); read_device(i2c, 0xFB, 0, &zero); read_device(i2c, 0xFF, 0, &zero); ret = write_device(i2c, reg, count, buf); read_device(i2c, 0xFE, 0, &zero); read_device(i2c, 0xFC, 0, &zero); i2c_unlock_adapter(i2c->adapter); i2c_unlock_adapter(i2c->adapter); return ret; }
// Update the LED for the given slot with the status int pal_set_led(uint8_t slot, uint8_t status) { char path[64] = {0}; char *val; if (slot < 1 || slot > 4) { return -1; } if (status) { val = "1"; } else { val = "0"; } sprintf(path, GPIO_VAL, gpio_led[slot]); if (write_device(path, val)) { return -1; } return 0; }
int pm860x_page_set_bits(struct i2c_client *i2c, int reg, unsigned char mask, unsigned char data) { unsigned char zero; unsigned char value; int ret; i2c_lock_adapter(i2c->adapter); read_device(i2c, 0xFA, 0, &zero); read_device(i2c, 0xFB, 0, &zero); read_device(i2c, 0xFF, 0, &zero); ret = read_device(i2c, reg, 1, &value); if (ret < 0) goto out; value &= ~mask; value |= data; ret = write_device(i2c, reg, 1, &value); out: read_device(i2c, 0xFE, 0, &zero); read_device(i2c, 0xFC, 0, &zero); i2c_unlock_adapter(i2c->adapter); return ret; }
int execute(void) { long long tmp; int cmp; switch(opcode) { //add case 0x18: ra += load_mem(&memory[path],3); break; //and case 0x40: ra &= load_mem(&memory[path],3); break; //comp // = -> 0b001 // > -> 0b010 // < -> 0b100 // save status in register sw case 0x28: cmp = load_mem(&memory[path],3); if(ra==cmp) rsw = 0x1; else if (ra>cmp) rsw = 0x2; else if (ra<cmp) rsw = 0x4; else rsw = 0; break; //div case 0x24: ra /= load_mem(&memory[path],3); break; //j case 0x3C: rpc = path; break; //jeq case 0x30: if(rsw==0x1) rpc = path; break; //jgt case 0x34: if(rsw==0x2) rpc = path; break; //jlt case 0x38: if(rsw==0x4) rpc = path; break; //jsub case 0x48: rl = rpc; rpc = path; break; //lda case 0x00: ra = load_mem(&memory[path],3); break; //ldch case 0x50: ra = (ra&0xFFFF00) + load_mem(&memory[path], 1); break; //ldl case 0x08: rl = load_mem(&memory[path],3); break; //ldx case 0x04: rx = load_mem(&memory[path],3); break; //mul case 0x20: tmp = (long long) ra * load_mem(&memory[path],3); ra = (int) (0xFFFFFF & tmp); break; //or case 0x44: ra |= load_mem(&memory[path],3); break; //rsub case 0x4C: rpc = rl; break; //sta case 0x0C: //incomplete save_mem(ra, &memory[path], 3); break; //stch case 0x54: save_mem(ra, &memory[path], 1); break; //stl case 0x14: save_mem(rl, &memory[path], 3); break; //stsw case 0xE8: save_mem(rsw, &memory[path], 3); break; //stx case 0x10: save_mem(rx, &memory[path], 3); break; //sub case 0x1C: ra -= load_mem(&memory[path], 3); break; //tix case 0x2C: cmp = load_mem(&memory[path],3); rx++; if(rx==cmp) rsw = 0x1; else if (rx>cmp) rsw = 0x2; else if (rx<cmp) rsw = 0x4; else rsw = 0; break; //td case 0xE0: rsw = test_device(memory[path]); break; //rd case 0xD8: ra = (ra&0xFFFF00) + read_device(memory[path]); break; //wd case 0xDC: write_device(memory[path], (ra&0x0000FF)); break; //break case 0xFF: return 10; break; default: printf("CPU Error: Could not found opcode\n"); printf("rpc= %06X\n", rpc); return 11; break; } return 0; }
// Switch the UART mux to the given slot int pal_switch_uart_mux(uint8_t slot) { char * gpio_uart_sel0; char * gpio_uart_sel1; char * gpio_uart_sel2; char * gpio_uart_rx; char path[64] = {0}; int ret; // Refer the UART select table in schematic switch(slot) { case 1: gpio_uart_sel2 = "0"; gpio_uart_sel1 = "0"; gpio_uart_sel0 = "1"; gpio_uart_rx = "0"; break; case 2: gpio_uart_sel2 = "0"; gpio_uart_sel1 = "0"; gpio_uart_sel0 = "0"; gpio_uart_rx = "0"; break; case 3: gpio_uart_sel2 = "0"; gpio_uart_sel1 = "1"; gpio_uart_sel0 = "1"; gpio_uart_rx = "0"; break; case 4: gpio_uart_sel2 = "0"; gpio_uart_sel1 = "1"; gpio_uart_sel0 = "0"; gpio_uart_rx = "0"; break; default: // for all other cases, assume BMC gpio_uart_sel2 = "1"; gpio_uart_sel1 = "0"; gpio_uart_sel0 = "0"; gpio_uart_rx = "1"; break; } // Diable TXD path from BMC to avoid conflict with SoL ret = control_sol_txd(slot); if (ret) { goto uart_exit; } // Enable Debug card path sprintf(path, GPIO_VAL, GPIO_UART_SEL2); ret = write_device(path, gpio_uart_sel2); if (ret) { goto uart_exit; } sprintf(path, GPIO_VAL, GPIO_UART_SEL1); ret = write_device(path, gpio_uart_sel1); if (ret) { goto uart_exit; } sprintf(path, GPIO_VAL, GPIO_UART_SEL0); ret = write_device(path, gpio_uart_sel0); if (ret) { goto uart_exit; } sprintf(path, GPIO_VAL, GPIO_UART_RX); ret = write_device(path, gpio_uart_rx); if (ret) { goto uart_exit; } uart_exit: if (ret) { syslog(LOG_ALERT, "pal_switch_uart_mux: write_device failed: %s\n", path); return ret; } else { return 0; } }
// Display the given POST code using GPIO port static int pal_post_display(uint8_t status) { char path[64] = {0}; int ret; char *val; syslog(LOG_ALERT, "pal_post_display: status is %d\n", status); sprintf(path, GPIO_VAL, GPIO_POSTCODE_0); if (BIT(status, 0)) { val = "1"; } else { val = "0"; } ret = write_device(path, val); if (ret) { goto post_exit; } sprintf(path, GPIO_VAL, GPIO_POSTCODE_1); if (BIT(status, 1)) { val = "1"; } else { val = "0"; } ret = write_device(path, val); if (ret) { goto post_exit; } sprintf(path, GPIO_VAL, GPIO_POSTCODE_2); if (BIT(status, 2)) { val = "1"; } else { val = "0"; } ret = write_device(path, val); if (ret) { goto post_exit; } sprintf(path, GPIO_VAL, GPIO_POSTCODE_3); if (BIT(status, 3)) { val = "1"; } else { val = "0"; } ret = write_device(path, val); if (ret) { goto post_exit; } sprintf(path, GPIO_VAL, GPIO_POSTCODE_4); if (BIT(status, 4)) { val = "1"; } else { val = "0"; } ret = write_device(path, val); if (ret) { goto post_exit; } sprintf(path, GPIO_VAL, GPIO_POSTCODE_5); if (BIT(status, 5)) { val = "1"; } else { val = "0"; } ret = write_device(path, val); if (ret) { goto post_exit; } sprintf(path, GPIO_VAL, GPIO_POSTCODE_6); if (BIT(status, 6)) { val = "1"; } else { val = "0"; } ret = write_device(path, val); if (ret) { goto post_exit; } sprintf(path, GPIO_VAL, GPIO_POSTCODE_7); if (BIT(status, 7)) { val = "1"; } else { val = "0"; } ret = write_device(path, val); if (ret) { goto post_exit; } post_exit: if (ret) { syslog(LOG_ALERT, "write_device failed for %s\n", path); return -1; } else { return 0; } }