int safte_read_config(struct safte_softc *sc) { struct safte_readbuf_cmd cmd; struct safte_config config; struct safte_sensor *s; int flags, i, j; memset(&cmd, 0, sizeof(cmd)); cmd.opcode = READ_BUFFER; cmd.flags |= SAFTE_RD_MODE; cmd.bufferid = SAFTE_RD_CONFIG; cmd.length = htobe16(sizeof(config)); flags = SCSI_DATA_IN; #ifndef SCSIDEBUG flags |= SCSI_SILENT; #endif if (cold) flags |= SCSI_AUTOCONF; if (scsi_scsi_cmd(sc->sc_link, (struct scsi_generic *)&cmd, sizeof(cmd), (u_char *)&config, sizeof(config), 2, 30000, NULL, flags) != 0) return (1); DPRINTF(("%s: nfans: %d npwrsup: %d nslots: %d doorlock: %d ntemps: %d" " alarm: %d celsius: %d ntherm: %d\n", DEVNAME(sc), config.nfans, config.npwrsup, config.nslots, config.doorlock, config.ntemps, config.alarm, SAFTE_CFG_CELSIUS(config.therm), SAFTE_CFG_NTHERM(config.therm))); sc->sc_encbuflen = config.nfans * sizeof(u_int8_t) + /* fan status */ config.npwrsup * sizeof(u_int8_t) + /* power supply status */ config.nslots * sizeof(u_int8_t) + /* device scsi id (lun) */ sizeof(u_int8_t) + /* door lock status */ sizeof(u_int8_t) + /* speaker status */ config.ntemps * sizeof(u_int8_t) + /* temp sensors */ sizeof(u_int16_t); /* temp out of range sensors */ sc->sc_encbuf = malloc(sc->sc_encbuflen, M_DEVBUF, M_NOWAIT); if (sc->sc_encbuf == NULL) return (1); sc->sc_nsensors = config.nfans + config.npwrsup + config.ntemps + (config.doorlock ? 1 : 0) + (config.alarm ? 1 : 0); sc->sc_sensors = malloc(sc->sc_nsensors * sizeof(struct safte_sensor), M_DEVBUF, M_NOWAIT | M_ZERO); if (sc->sc_sensors == NULL) { free(sc->sc_encbuf, M_DEVBUF); sc->sc_encbuf = NULL; sc->sc_nsensors = 0; return (1); } strlcpy(sc->sc_sensordev.xname, DEVNAME(sc), sizeof(sc->sc_sensordev.xname)); s = sc->sc_sensors; for (i = 0; i < config.nfans; i++) { s->se_type = SAFTE_T_FAN; s->se_field = (u_int8_t *)(sc->sc_encbuf + i); s->se_sensor.type = SENSOR_INDICATOR; snprintf(s->se_sensor.desc, sizeof(s->se_sensor.desc), "Fan%d", i); s++; } j = config.nfans; for (i = 0; i < config.npwrsup; i++) { s->se_type = SAFTE_T_PWRSUP; s->se_field = (u_int8_t *)(sc->sc_encbuf + j + i); s->se_sensor.type = SENSOR_INDICATOR; snprintf(s->se_sensor.desc, sizeof(s->se_sensor.desc), "PSU%d", i); s++; } j += config.npwrsup; #if NBIO > 0 sc->sc_nslots = config.nslots; sc->sc_slots = (u_int8_t *)(sc->sc_encbuf + j); #endif j += config.nslots; if (config.doorlock) { s->se_type = SAFTE_T_DOORLOCK; s->se_field = (u_int8_t *)(sc->sc_encbuf + j); s->se_sensor.type = SENSOR_INDICATOR; strlcpy(s->se_sensor.desc, "doorlock", sizeof(s->se_sensor.desc)); s++; } j++; if (config.alarm) { s->se_type = SAFTE_T_ALARM; s->se_field = (u_int8_t *)(sc->sc_encbuf + j); s->se_sensor.type = SENSOR_INDICATOR; strlcpy(s->se_sensor.desc, "alarm", sizeof(s->se_sensor.desc)); s++; } j++; /* * stash the temp info so we can get out of range status. limit the * number so the out of temp checks cant go into memory it doesnt own */ sc->sc_ntemps = (config.ntemps > 15) ? 15 : config.ntemps; sc->sc_temps = s; sc->sc_celsius = SAFTE_CFG_CELSIUS(config.therm); for (i = 0; i < config.ntemps; i++) { s->se_type = SAFTE_T_TEMP; s->se_field = (u_int8_t *)(sc->sc_encbuf + j + i); s->se_sensor.type = SENSOR_TEMP; s++; } j += config.ntemps; sc->sc_temperrs = (u_int16_t *)(sc->sc_encbuf + j); return (0); }
int safte_read_config(struct safte_softc *sc) { struct safte_config *config = NULL; struct safte_readbuf_cmd *cmd; struct safte_sensor *s; struct scsi_xfer *xs; int error = 0, flags = 0, i, j; config = dma_alloc(sizeof(*config), PR_NOWAIT); if (config == NULL) return (1); if (cold) flags |= SCSI_AUTOCONF; xs = scsi_xs_get(sc->sc_link, flags | SCSI_DATA_IN | SCSI_SILENT); if (xs == NULL) { error = 1; goto done; } xs->cmdlen = sizeof(*cmd); xs->data = (void *)config; xs->datalen = sizeof(*config); xs->retries = 2; xs->timeout = 30000; cmd = (struct safte_readbuf_cmd *)xs->cmd; cmd->opcode = READ_BUFFER; cmd->flags |= SAFTE_RD_MODE; cmd->bufferid = SAFTE_RD_CONFIG; cmd->length = htobe16(sizeof(*config)); error = scsi_xs_sync(xs); scsi_xs_put(xs); if (error != 0) { error = 1; goto done; } DPRINTF(("%s: nfans: %d npwrsup: %d nslots: %d doorlock: %d ntemps: %d" " alarm: %d celsius: %d ntherm: %d\n", DEVNAME(sc), config->nfans, config->npwrsup, config->nslots, config->doorlock, config->ntemps, config->alarm, SAFTE_CFG_CELSIUS(config->therm), SAFTE_CFG_NTHERM(config->therm))); sc->sc_encbuflen = config->nfans * sizeof(u_int8_t) + /* fan status */ config->npwrsup * sizeof(u_int8_t) + /* power supply status */ config->nslots * sizeof(u_int8_t) + /* device scsi id (lun) */ sizeof(u_int8_t) + /* door lock status */ sizeof(u_int8_t) + /* speaker status */ config->ntemps * sizeof(u_int8_t) + /* temp sensors */ sizeof(u_int16_t); /* temp out of range sensors */ sc->sc_encbuf = dma_alloc(sc->sc_encbuflen, PR_NOWAIT); if (sc->sc_encbuf == NULL) { error = 1; goto done; } sc->sc_nsensors = config->nfans + config->npwrsup + config->ntemps + (config->doorlock ? 1 : 0) + (config->alarm ? 1 : 0); sc->sc_sensors = mallocarray(sc->sc_nsensors, sizeof(struct safte_sensor), M_DEVBUF, M_NOWAIT | M_ZERO); if (sc->sc_sensors == NULL) { dma_free(sc->sc_encbuf, sc->sc_encbuflen); sc->sc_encbuf = NULL; sc->sc_nsensors = 0; error = 1; goto done; } strlcpy(sc->sc_sensordev.xname, DEVNAME(sc), sizeof(sc->sc_sensordev.xname)); s = sc->sc_sensors; for (i = 0; i < config->nfans; i++) { s->se_type = SAFTE_T_FAN; s->se_field = (u_int8_t *)(sc->sc_encbuf + i); s->se_sensor.type = SENSOR_INDICATOR; snprintf(s->se_sensor.desc, sizeof(s->se_sensor.desc), "Fan%d", i); s++; } j = config->nfans; for (i = 0; i < config->npwrsup; i++) { s->se_type = SAFTE_T_PWRSUP; s->se_field = (u_int8_t *)(sc->sc_encbuf + j + i); s->se_sensor.type = SENSOR_INDICATOR; snprintf(s->se_sensor.desc, sizeof(s->se_sensor.desc), "PSU%d", i); s++; } j += config->npwrsup; #if NBIO > 0 sc->sc_nslots = config->nslots; sc->sc_slots = (u_int8_t *)(sc->sc_encbuf + j); #endif j += config->nslots; if (config->doorlock) { s->se_type = SAFTE_T_DOORLOCK; s->se_field = (u_int8_t *)(sc->sc_encbuf + j); s->se_sensor.type = SENSOR_INDICATOR; strlcpy(s->se_sensor.desc, "doorlock", sizeof(s->se_sensor.desc)); s++; } j++; if (config->alarm) { s->se_type = SAFTE_T_ALARM; s->se_field = (u_int8_t *)(sc->sc_encbuf + j); s->se_sensor.type = SENSOR_INDICATOR; strlcpy(s->se_sensor.desc, "alarm", sizeof(s->se_sensor.desc)); s++; } j++; /* * stash the temp info so we can get out of range status. limit the * number so the out of temp checks cant go into memory it doesnt own */ sc->sc_ntemps = (config->ntemps > 15) ? 15 : config->ntemps; sc->sc_temps = s; sc->sc_celsius = SAFTE_CFG_CELSIUS(config->therm); for (i = 0; i < config->ntemps; i++) { s->se_type = SAFTE_T_TEMP; s->se_field = (u_int8_t *)(sc->sc_encbuf + j + i); s->se_sensor.type = SENSOR_TEMP; s++; } j += config->ntemps; sc->sc_temperrs = (u_int8_t *)(sc->sc_encbuf + j); done: dma_free(config, sizeof(*config)); return (error); }