static int kexec_reboot(struct boot_task *task) { int result; /* First try running shutdown. Init scripts should run 'exec -e' */ result = process_run_simple(task, pb_system_apps.shutdown, "-r", "now", NULL); /* On error, force a kexec with the -e option */ if (result) { result = process_run_simple(task, pb_system_apps.kexec, "-e", NULL); } if (result) pb_log("%s: failed: (%d)\n", __func__, result); /* okay, kexec -e -f */ if (result) { result = process_run_simple(task, pb_system_apps.kexec, "-e", "-f", NULL); } if (result) pb_log("%s: failed: (%d)\n", __func__, result); return result; }
static void *pcore_thread_recv_send(void *arg) { pb_core_t *core = NULL; prctl(PR_SET_NAME, "pbyte_rs_switcher", 0, 0, 0); if (!arg) goto err; core = (pb_core_t *)arg; pcore_thread_init (core); pb_log (core, PBYTE_INFO, "Recv/Send switcher thread: Inited"); while (core->active) { pcore_check_send (core); pcore_check_recv (core); } pb_log (core, PBYTE_INFO, "Recv/Send switcher thread: Normal exit"); return NULL; err: pb_log (core, PBYTE_ERR, "Recv/Send switcher thread: Force exit"); return NULL; }
int platform_init(void *ctx) { extern struct platform *__start_platforms, *__stop_platforms; struct platform **p; platform_ctx = talloc_new(ctx); for (p = &__start_platforms; p < &__stop_platforms; p++) { pb_debug("%s: Try platform %s\n", __func__, (*p)->name); if (!(*p)->probe(*p, platform_ctx)) continue; platform = *p; break; } config = talloc(platform_ctx, struct config); config_set_defaults(config); if (platform) { pb_log("Detected platform type: %s\n", platform->name); if (platform->load_config) platform->load_config(platform, config); } else { pb_log("No platform type detected, some platform-specific " "functionality will be disabled\n"); } dump_config(config); return 0; }
static void run_boot_hooks(struct boot_task *task) { struct dirent **hooks; int i, n; n = scandir(boot_hook_dir, &hooks, hook_filter, hook_cmp); if (n < 1) return; update_status(task->status_fn, task->status_arg, BOOT_STATUS_INFO, _("running boot hooks")); boot_hook_setenv(task); for (i = 0; i < n; i++) { const char *argv[2] = { NULL, NULL }; struct process *process; char *path; int rc; path = join_paths(task, boot_hook_dir, hooks[i]->d_name); if (access(path, X_OK)) { talloc_free(path); continue; } process = process_create(task); argv[0] = path; process->path = path; process->argv = argv; process->keep_stdout = true; pb_log("running boot hook %s\n", hooks[i]->d_name); rc = process_run_sync(process); if (rc) { pb_log("boot hook exec failed!\n"); } else if (WIFEXITED(process->exit_status) && WEXITSTATUS(process->exit_status) == BOOT_HOOK_EXIT_UPDATE) { /* if the hook returned with BOOT_HOOK_EXIT_UPDATE, * then we process stdout to look for updated params */ boot_hook_update(task, hooks[i]->d_name, process->stdout_buf); boot_hook_setenv(task); } process_release(process); talloc_free(path); } free(hooks); }
static void *pcore_thread_worker(void *arg) { pb_core_t *core = NULL; pb_msg_t *pb_msg = NULL; prctl(PR_SET_NAME, "pbyte_worker", 0, 0, 0); if (!arg) return NULL; core = (pb_core_t *)arg; pcore_thread_init (core); pb_log (core, PBYTE_INFO, "Worker thread: Inited"); while (core->active) { pb_msg = (pb_msg_t *)mqueue_timedget_msec(&core->queue_in, MSG_TIMEOUT); if (pb_msg != NULL) { #ifdef QUEUE_DEBUG int qelems = mqueue_get_count(&core->queue_in); pb_log (core, (qelems > 1)? PBYTE_INFO:PBYTE_CUT, "GET message from INPUT queue. " "Message in INPUT queue: %d", qelems); #endif pb_msg_print(&core->logger, PBYTE_INFO, "input", pb_msg); #ifdef TIME_DEBUG pb_print_msg_time(&core->logger, "Input queue -> RServer", pb_msg); #endif if (core->message_handler) core->message_handler(core->application, pb_msg); pb_msg_unpack_free (&pb_msg); } } pb_log (core, PBYTE_INFO, "Worker thread: Normal exit"); return NULL; }
static int ipmi_recv(struct ipmi *ipmi, uint8_t *netfn, uint8_t *cmd, long *seq, uint8_t *buf, uint16_t *len) { struct ipmi_recv recv; struct ipmi_addr addr; int rc; recv.addr = (unsigned char *)&addr; recv.addr_len = sizeof(addr); recv.msg.data = buf; recv.msg.data_len = *len; rc = ioctl(ipmi->fd, IPMICTL_RECEIVE_MSG_TRUNC, &recv); if (rc < 0 && errno != EMSGSIZE) { pb_log("IPMI: recv (%d bytes) failed: %m\n", *len); return -1; } else if (rc < 0 && errno == EMSGSIZE) { pb_debug("IPMI: truncated message (netfn %d, cmd %d, " "size %d), continuing anyway\n", recv.msg.netfn, recv.msg.cmd, *len); } *netfn = recv.msg.netfn; *cmd = recv.msg.cmd; *seq = recv.msgid; *len = recv.msg.data_len; return 0; }
static int ipmi_send(struct ipmi *ipmi, uint8_t netfn, uint8_t cmd, uint8_t *buf, uint16_t len) { struct ipmi_system_interface_addr addr; struct ipmi_req req; int rc; memset(&addr, 0, sizeof(addr)); addr.addr_type = IPMI_SYSTEM_INTERFACE_ADDR_TYPE; addr.channel = IPMI_BMC_CHANNEL; memset(&req, 0, sizeof(req)); req.addr = (unsigned char *)&addr; req.addr_len = sizeof(addr); req.msgid = ipmi->seq++; req.msg.data = buf; req.msg.data_len = len; req.msg.netfn = netfn; req.msg.cmd = cmd; rc = ioctl(ipmi->fd, IPMICTL_SEND_COMMAND, &req); if (rc < 0) { pb_log("IPMI: send (netfn %d, cmd %d, %d bytes) failed: %m\n", netfn, cmd, len); return -1; } return 0; }
static void boot_hook_update(struct boot_task *task, const char *hookname, char *buf) { char *line, *name, *val, *sep; char *saveptr = NULL; for (;; buf = NULL) { line = strtok_r(buf, "\n", &saveptr); if (!line) break; sep = strchr(line, '='); if (!sep) continue; *sep = '\0'; name = line; val = sep + 1; boot_hook_update_param(task, task, name, val); pb_log("boot hook %s specified %s=%s\n", hookname, name, val); } }
void ui_timer_init(struct waitset *waitset, struct ui_timer *timer, unsigned int seconds) { pb_log("%s: %u\n", __func__, seconds); timer->timeout = seconds; timer->waitset = waitset; }
struct pjs *pjs_init(void *ctx, int (*map)(const struct js_event *)) { static const char dev_name[] = "/dev/input/js0"; struct pjs *pjs; pjs = talloc_zero(ctx, struct pjs); if (!pjs) return NULL; pjs->map = map; pjs->fd = open(dev_name, O_RDONLY | O_NONBLOCK); if (pjs->fd < 0) { pb_log("%s: open %s failed: %s\n", __func__, dev_name, strerror(errno)); goto out_err; } talloc_set_destructor(pjs, pjs_destructor); pb_debug("%s: using %s\n", __func__, dev_name); return pjs; out_err: close(pjs->fd); pjs->fd = 0; talloc_free(pjs); return NULL; }
static int pcore_recv_identity (pb_core_t *core, pb_identity_t *identity) { zmq_msg_t msg; int rc, more; zmq_msg_init (&msg); rc = zmq_recvmsg (core->sock, &msg, 0); if (rc < 0) { pb_log (core, PBYTE_WARN, "Recieve identity failed: %s", zmq_strerror(zmq_errno())); zmq_msg_close(&msg); return -1; } more = zmq_msg_more (&msg); if (more != 1) { pb_log (core, PBYTE_WARN, "No more data after identity"); zmq_msg_close(&msg); return -2; } if (zmq_msg_size (&msg) >= PBYTE_IDENTITY_LEN) { pb_log (core, PBYTE_WARN, "Recieve message failed. " "Large identity"); zmq_msg_close(&msg); return -3; } // pb_print_buff (&core->logger, PBYTE_INFO, // "incomming identity", // zmq_msg_data(msg), // zmq_msg_size(msg)); memcpy (identity->identity, zmq_msg_data (&msg), zmq_msg_size (&msg)); identity->identity_len = zmq_msg_size (&msg); zmq_msg_close(&msg); return 0; }
void _pb_log_fn(const char *func, const char *fmt, ...) { va_list ap; pb_log("%s: ", func); va_start(ap, fmt); __log(fmt, ap); va_end(ap); }
void ui_timer_disable(struct ui_timer *timer) { if (!timer->waiter) return; pb_log("%s\n", __func__); waiter_remove(timer->waiter); timer->waiter = NULL; }
int pcore_stop(void *core_ptr) { int rc = 0, i; pb_core_t *core = NULL; if (!core_ptr) return 0; core = (pb_core_t *)core_ptr; pb_log (core, PBYTE_WARN, "Stop detected"); if (!core->active) return 0; core->active = 0; rc = pthread_join (core->thread_recv_send, NULL); for (i = 0; i < core->worker_count; i++) { rc |= pthread_join (core->thread_worker[i], NULL); } if (rc == 0) { sleep (1); zmq_unbind (core->sock, core->URL); zmq_close (core->sock); zmq_ctx_destroy (core->ctx); mqueue_close (&core->queue_in); mqueue_close (&core->queue_out); pcore_init (core); } pb_log (core, PBYTE_INFO, "Stop success [%d]", rc); free (core); return rc; }
void _pb_debug_fn(const char *func, const char *fmt, ...) { va_list ap; if (!debug) return; pb_log("%s: ", func); va_start(ap, fmt); __log(fmt, ap); va_end(ap); }
void _pb_debug_fl(const char *func, int line, const char *fmt, ...) { va_list ap; if (!debug) return; pb_log("%s:%d: ", func, line); va_start(ap, fmt); __log(fmt, ap); va_end(ap); }
static int cdrom_open(const char *devpath, const char *loc) { int fd; fd = open(devpath, O_RDONLY | O_NONBLOCK); if (fd < 0) pb_log("%s: can't open %s: %s\n", loc, devpath, strerror(errno)); return fd; }
void cdrom_eject(const char *devpath) { int fd, rc; fd = cdrom_open(devpath, __func__); if (fd < 0) return; /* unlock cdrom device */ rc = ioctl(fd, CDROM_LOCKDOOR, 0); if (rc < 0) pb_log("%s: CDROM_LOCKDOOR(unlock) failed: %s\n", __func__, strerror(errno)); rc = ioctl(fd, CDROMEJECT, 0); if (rc < 0) pb_log("%s: CDROM_EJECT failed: %s\n", __func__, strerror(errno)); close(fd); }
int config_set(struct config *newconfig) { int rc; if (!platform || !platform->save_config) return -1; if (newconfig == config) return 0; pb_log("new configuration data received\n"); dump_config(newconfig); rc = platform->save_config(platform, newconfig); if (!rc) config = talloc_steal(platform_ctx, newconfig); else pb_log("error saving new configuration; changes lost\n"); return rc; }
int pcore_msg_send (void *core_ptr, pb_msg_t *pb_msg) { int rc; pb_core_t *core = NULL; if (!core_ptr || !pb_msg) goto err; core = (pb_core_t *)core_ptr; rc = mqueue_put (&core->queue_out, (void *)pb_msg, 0); if (rc < 0) { pb_log (core, PBYTE_ERR, "Send failed. " "Failed to put message in queue [%d]", rc); goto err; } #ifdef QUEUE_DEBUG int qelems = mqueue_get_count(&core->queue_in); pb_log (core, (qelems > 1)? PBYTE_INFO:PBYTE_CUT, "PUT message to OUTPUT queue. " "Message in OUTPUT queue: %d", qelems); #endif return 0; err: pcore_proc_error (core, pb_msg); if (pb_msg) pb_msg_unpack_free (&pb_msg); return -1; }
int pjs_process_event(const struct pjs *pjs) { int result; struct js_event e; assert(pjs->fd); result = read(pjs->fd, &e, sizeof(e)); if (result != sizeof(e)) { pb_log("%s: read failed: %s\n", __func__, strerror(errno)); return 0; } return pjs->map(&e); }
/** * kexec_load - kexec load helper. */ static int kexec_load(struct boot_task *boot_task) { int result; const char *argv[7]; const char **p; char *s_initrd = NULL; char *s_dtb = NULL; char *s_args = NULL; p = argv; *p++ = pb_system_apps.kexec; /* 1 */ *p++ = "-l"; /* 2 */ if (boot_task->local_initrd) { s_initrd = talloc_asprintf(boot_task, "--initrd=%s", boot_task->local_initrd); assert(s_initrd); *p++ = s_initrd; /* 3 */ } if (boot_task->local_dtb) { s_dtb = talloc_asprintf(boot_task, "--dtb=%s", boot_task->local_dtb); assert(s_dtb); *p++ = s_dtb; /* 4 */ } if (boot_task->args) { s_args = talloc_asprintf(boot_task, "--append=%s", boot_task->args); assert(s_args); *p++ = s_args; /* 5 */ } *p++ = boot_task->local_image; /* 6 */ *p++ = NULL; /* 7 */ result = process_run_simple_argv(boot_task, argv); if (result) pb_log("%s: failed: (%d)\n", __func__, result); return result; }
struct ipmi *ipmi_open(void *ctx) { struct ipmi *ipmi; int fd; fd = open(ipmi_devnode, O_RDWR); if (fd < 0) { pb_log("IPMI: can't open IPMI device %s: %m\n", ipmi_devnode); return NULL; } ipmi = talloc(ctx, struct ipmi); ipmi->fd = fd; ipmi->seq = 0; talloc_set_destructor(ipmi, ipmi_destroy); return ipmi; }
int cui_run_cmd(struct pmenu_item *item) { int result; struct cui *cui = cui_from_item(item); const char **cmd_argv = item->data; nc_scr_status_printf(cui->current, _("Running %s..."), cmd_argv[0]); def_prog_mode(); result = process_run_simple_argv(item, cmd_argv); reset_prog_mode(); redrawwin(cui->current->main_ncw); if (result) { pb_log("%s: failed: '%s'\n", __func__, cmd_argv[0]); nc_scr_status_printf(cui->current, _("Failed: %s"), cmd_argv[0]); } return result; }
static int pcore_check_send (pb_core_t *core) { int rc = -1, size = 0, budget; char *data = NULL, *output_data = NULL; pb_msg_t *pb_msg = NULL; char identity_str[256] = {0}; if (!core) return -1; budget = BUDGET; while (--budget > 0) { data = mqueue_timedget_msec (&core->queue_out, MSG_TIMEOUT); if (!data) break; #ifdef QUEUE_DEBUG int qelems = mqueue_get_count(&core->queue_out); pb_log (core, (qelems > 1)? PBYTE_INFO:PBYTE_CUT, "GET message from OUTPUT queue. " "Message in OUTPUT queue: %d", qelems); #endif pb_msg = (pb_msg_t *)data; pb_pb_identity_to_str (&pb_msg->identity, 1, identity_str, sizeof (identity_str)); pb_log (core, PBYTE_INFO, "%s: Send '%s'", identity_str, pb_pb_msg_type_to_str (pb_msg->message_params.msg_type)); pb_msg_print (&core->logger, PBYTE_INFO, "output", pb_msg); rc = pb_msg_pack (pb_msg, &output_data, &size); if (rc < 0 || size <= 0 || !output_data) { pb_log (core, PBYTE_ERR, "Failed to pack message. " "Skip message"); goto skip_message; } // pb_print_buff (&core->logger, PBYTE_INFO, // "output message", // output_data, size); if (core->mode == ePBYTE_SERVER) { #ifdef TIME_DEBUG pb_print_msg_time(&core->logger, "Output queue -> send", pb_msg); #endif /* send identity first for ZMQ-routing */ rc = zmq_send (core->sock, pb_msg->identity.identity, pb_msg->identity.identity_len, ZMQ_SNDMORE); if (rc != pb_msg->identity.identity_len) { pb_log (core, PBYTE_WARN, "Send identity failed: %s", zmq_strerror(zmq_errno())); goto skip_message; } } rc = zmq_send (core->sock, output_data, size, 0); if (rc != size) { pb_log (core, PBYTE_WARN, "Send message failed: %s", zmq_strerror(zmq_errno())); goto skip_message; } pb_log (core, PBYTE_INFO, "%s: '%s': Message was sent", identity_str, pb_pb_msg_type_to_str(pb_msg->message_params.msg_type)); pb_msg_pack_free (&output_data); pb_msg_unpack_free (&pb_msg); } return 0; skip_message: pcore_proc_error (core, pb_msg); if (output_data) pb_msg_pack_free (&output_data); if (pb_msg) pb_msg_unpack_free (&pb_msg); return rc; }
static int pcore_check_recv (pb_core_t *core) { int rc, count, budget; zmq_msg_t msg; pb_msg_t *pb_msg = NULL; pb_identity_t identity = {0}; budget = BUDGET; while (--budget > 0) { count = zmq_poll (&core->pollitem, 1, MSG_TIMEOUT); if (!count) break; zmq_msg_init (&msg); if (count < 0) { pb_log (core, PBYTE_WARN, "Poll: %s", zmq_strerror(zmq_errno())); goto skip_message; } if (core->mode == ePBYTE_SERVER) { /* identity comes first */ if (pcore_recv_identity (core, &identity) != 0) goto skip_message; } /* then the first part of the message body */ rc = zmq_recvmsg (core->sock, &msg, 0); if (rc <= 0) { pb_log (core, PBYTE_WARN, "Recieve message failed: %s", zmq_strerror(zmq_errno())); goto skip_message; } // pb_print_buff (&core->logger, PBYTE_INFO, // "incomming message", // zmq_msg_data(msg), // zmq_msg_size(msg)); rc = pb_msg_unpack (&pb_msg, (char *)zmq_msg_data(&msg), zmq_msg_size(&msg)); if (rc != 0) { pb_log (core, PBYTE_WARN, "Recieve message failed. " "Failed to unpack message"); goto skip_message; } pb_msg_set_identity (pb_msg, &identity); #ifdef TIME_DEBUG pb_clockgettime(&pb_msg->start); #endif rc = mqueue_put(&core->queue_in, (void *)pb_msg, 0); if (rc < 0) { pb_log (core, PBYTE_WARN, "Recieve message failed. " "Failed to put message in queue"); goto skip_message; } #ifdef QUEUE_DEBUG int qelems = mqueue_get_count(&core->queue_in); pb_log (core, (qelems > 1)? PBYTE_INFO:PBYTE_CUT, "PUT message to INPUT queue. " "Messages in INPUT queue: %d", qelems); #endif pb_msg = NULL; zmq_msg_close(&msg); } return 0; skip_message: if (pb_msg) pb_msg_unpack_free (&pb_msg); zmq_msg_close(&msg); return -1; }
int pcore_start (void **core_ptr, pcore_params_t *pcore_params, void *application) { int rc = 0, i; pb_core_t *core = NULL; if (!pcore_params || !application) { rc = -1; goto err; } *core_ptr = (pb_core_t *)calloc(1, sizeof (pb_core_t)); if (!*core_ptr) { rc = -1; goto err; } core = *core_ptr; pcore_init(core); if (pcore_params->mode != ePBYTE_SERVER && pcore_params->mode != ePBYTE_CLIENT) { rc = -2; goto err; } core->mode = pcore_params->mode; core->application = application; if (pcore_params->message_handler) core->message_handler = pcore_params->message_handler; if (pcore_params->error_handler) core->error_handler = pcore_params->error_handler; if (pcore_params->logger) { sprintf (core->logger.prefix, "PCORE_%s:", (pcore_params->mode == ePBYTE_SERVER)? "S":"C"); pb_log_set_logger (&core->logger, pcore_params->logger); pb_log_set_prio (&core->logger, pcore_params->logger_prio); } if (pcore_params->thread_init) { core->thread_init = pcore_params->thread_init; } else { pb_log (core, PBYTE_ERR, "Failed to start. " "Thread init callback not set"); rc = -2; goto err; } if (!pcore_params->addr || (pcore_params->port <= 0 || 65535 <= pcore_params->port) || (pcore_params->io_threads <= 0)) { pb_log (core, PBYTE_ERR, "Failed to start. " "Invalid params"); rc = -3; goto err; } if (pcore_params->worker_count <= 0 || pcore_params->worker_count >= MAX_WORKER_COUNT) { core->worker_count = DEF_WORKER_COUNT; } else { core->worker_count = pcore_params->worker_count; } sprintf(core->URL, "tcp://%s:%d", pcore_params->addr, pcore_params->port); core->ctx = zmq_init (pcore_params->io_threads); if (!core->ctx) { pb_log (core, PBYTE_ERR, "Failed to start. " "Can't init context: %s", zmq_strerror(zmq_errno())); rc = -4; goto err; } if (pcore_params->mode == ePBYTE_SERVER) { core->sock = zmq_socket (core->ctx, ZMQ_ROUTER); if (!core->sock) { pb_log (core, PBYTE_ERR, "Failed to start. " "Can't init socket: %s", zmq_strerror(zmq_errno())); rc = -5; goto err; } pb_log (core, PBYTE_INFO, "Try bind in '%s'", core->URL); rc = zmq_bind (core->sock, core->URL); if (rc != 0) { pb_log (core, PBYTE_ERR, "Failed to start. " "Bind failed: %s", zmq_strerror(zmq_errno())); rc = -6; goto err; } } else { core->sock = zmq_socket (core->ctx, ZMQ_DEALER); if (!core->sock) { pb_log (core, PBYTE_ERR, "Failed to start. " "Can't init socket: %s", zmq_strerror(zmq_errno())); rc = -5; goto err; } rc = zmq_setsockopt (core->sock, ZMQ_IDENTITY, pcore_params->identity.identity, strlen(pcore_params->identity.identity)); if (rc != 0) { pb_log (core, PBYTE_ERR, "Failed to set identity: %s", zmq_strerror(zmq_errno())); rc = -6; goto err; } pb_log (core, PBYTE_INFO, "Try connect to '%s'", core->URL); rc = zmq_connect (core->sock, core->URL); if (rc != 0) { pb_log (core, PBYTE_ERR, "Failed to start. " "Connect failed: %s", zmq_strerror(zmq_errno())); rc = -6; goto err; } } mqueue_init (&core->queue_in, MQUEUESIZE); mqueue_init (&core->queue_out, MQUEUESIZE); core->pollitem.socket = core->sock; core->pollitem.fd = 0; core->pollitem.events = ZMQ_POLLIN; core->pollitem.revents = 0; core->active = 1; rc = pthread_create(&core->thread_recv_send, NULL, &pcore_thread_recv_send, (void *)core); if(rc < 0) { pb_log (core, PBYTE_ERR, "Failed to start. " "Can't create recv/send switcher thread: %s", strerror(errno)); rc = -7; goto err; } for (i = 0; i < core->worker_count; i++) { rc = pthread_create (&core->thread_worker[i], NULL, &pcore_thread_worker, (void *)core); if(rc < 0) { pb_log (core, PBYTE_ERR, "Failed to start. " "Can't create primary worker%d thread: %s", i, strerror(errno)); rc = -8 - i; goto err; } } pb_log (core, PBYTE_INFO, "Start success. Worker count: %d", core->worker_count); return 0; err: switch(rc) { case -7: if (core && core->sock) zmq_unbind (core->sock, core->URL); case -6: if (core && core->sock) zmq_close (core->sock); case -5: if (core && core->ctx) zmq_ctx_destroy (core->ctx); case -4: case -3: case -2: free (core); case -1: break; default: pcore_stop (core); break; } return rc; }
/* Reads and applies an IPMI interface config override, which closely follows * the format of an interface config struct as described in lib/types */ void parse_ipmi_interface_override(struct config *config, uint8_t *buf, uint16_t len) { struct interface_config *ifconf; char *ipstr, *gatewaystr; uint8_t hwsize, ipsize; int addr_type, i = 0; socklen_t addr_len; /* Get 1-byte hardware address size and ip address size */ memcpy(&hwsize, &buf[i], sizeof(hwsize)); i += sizeof(hwsize); memcpy(&ipsize, &buf[i], sizeof(ipsize)); i += sizeof(ipsize); if (!hwsize || !ipsize) { pb_log("%s: Empty response\n", __func__); return; } /* At the moment only support 6-byte MAC addresses */ if (hwsize != sizeof(ifconf->hwaddr)) { pb_log("Unsupported HW address size in network override: %u\n", hwsize); return; } /* Sanity check the IP address size */ if (ipsize == 4) { addr_type = AF_INET; addr_len = INET_ADDRSTRLEN; } else if (ipsize == 16) { addr_type = AF_INET6; addr_len = INET6_ADDRSTRLEN; } else { pb_log("Unsupported IP address size: %u\n", ipsize); return; } /* Everything past here is the interface config */ ifconf = talloc_zero(config, struct interface_config); if (!ifconf) { pb_log("Failed to allocate network override\n"); return; } /* Hardware Address */ memcpy(ifconf->hwaddr, &buf[i], hwsize); i += hwsize; /* Check 1-byte ignore and method flags */ ifconf->ignore = !!buf[i++]; ifconf->method = !!buf[i++]; if (ifconf->method == CONFIG_METHOD_STATIC) { if (ipsize + ipsize + 1 > len - i) { pb_log("Expected data greater than buffer size\n"); talloc_free(ifconf); return; } /* IP address */ ipstr = talloc_array(ifconf, char, addr_len); if (!inet_ntop(addr_type, &buf[i], ipstr, addr_len)) { pb_log("Failed to convert ipaddr: %m\n"); talloc_free(ifconf); return; } i += ipsize; /* IP address subnet */ ifconf->static_config.address = talloc_asprintf(ifconf, "%s/%u", ipstr, buf[i]); i++; /* Gateway address */ gatewaystr = talloc_array(ifconf, char, addr_len); if (!inet_ntop(addr_type, &buf[i], gatewaystr, addr_len)) { pb_log("Failed to convert gateway: %m\n"); talloc_free(ifconf); return; } ifconf->static_config.gateway = gatewaystr; i += ipsize; } pb_log("Applying IPMI network config\n"); /* Replace any existing interface config */ talloc_free(config->network.interfaces); config->network.n_interfaces = 1; config->network.interfaces = talloc(config, struct interface_config *); config->network.interfaces[0] = ifconf; }
void cui_abort(struct cui *cui) { pb_log("%s: exiting\n", __func__); cui->abort = 1; }
struct boot_task *boot(void *ctx, struct discover_boot_option *opt, struct boot_command *cmd, int dry_run, boot_status_fn status_fn, void *status_arg) { struct pb_url *image = NULL, *initrd = NULL, *dtb = NULL; struct boot_task *boot_task; const char *boot_desc; int rc; if (opt && opt->option->name) boot_desc = opt->option->name; else if (cmd && cmd->boot_image_file) boot_desc = cmd->boot_image_file; else boot_desc = _("(unknown)"); update_status(status_fn, status_arg, BOOT_STATUS_INFO, _("Booting %s."), boot_desc); if (cmd && cmd->boot_image_file) { image = pb_url_parse(opt, cmd->boot_image_file); } else if (opt && opt->boot_image) { image = opt->boot_image->url; } else { pb_log("%s: no image specified\n", __func__); update_status(status_fn, status_arg, BOOT_STATUS_INFO, _("Boot failed: no image specified")); return NULL; } if (cmd && cmd->initrd_file) { initrd = pb_url_parse(opt, cmd->initrd_file); } else if (opt && opt->initrd) { initrd = opt->initrd->url; } if (cmd && cmd->dtb_file) { dtb = pb_url_parse(opt, cmd->dtb_file); } else if (opt && opt->dtb) { dtb = opt->dtb->url; } boot_task = talloc_zero(ctx, struct boot_task); boot_task->dry_run = dry_run; boot_task->status_fn = status_fn; boot_task->status_arg = status_arg; if (cmd && cmd->boot_args) { boot_task->args = talloc_strdup(boot_task, cmd->boot_args); } else if (opt && opt->option->boot_args) { boot_task->args = talloc_strdup(boot_task, opt->option->boot_args); } else { boot_task->args = NULL; } /* start async loads for boot resources */ rc = start_url_load(boot_task, "kernel image", image, &boot_task->image) || start_url_load(boot_task, "initrd", initrd, &boot_task->initrd) || start_url_load(boot_task, "dtb", dtb, &boot_task->dtb); /* If all URLs are local, we may be done. */ if (rc) { talloc_free(boot_task); return NULL; } boot_process(NULL, boot_task); return boot_task; }