static bool bitforce_get_temp(struct cgpu_info *bitforce) { int fdDev = bitforce->device_fd; char pdevbuf[0x100]; char *s; if (!fdDev) return false; /* Do not try to get the temperature if we're polling for a result to * minimise the chance of interleaved results */ if (bitforce->polling) return true; // Flash instead of Temp - doing both can be too slow if (bitforce->flash_led) { bitforce_flash_led(bitforce); return true; } /* It is not critical getting temperature so don't get stuck if we * can't grab the mutex here */ if (mutex_trylock(&bitforce->device_mutex)) return false; BFwrite(fdDev, "ZLX", 3); pdevbuf[0] = '\0'; BFgets(pdevbuf, sizeof(pdevbuf), fdDev); mutex_unlock(&bitforce->device_mutex); if (unlikely(!pdevbuf[0])) { applog(LOG_ERR, "BFL%i: Error: Get temp returned empty string/timed out", bitforce->device_id); bitforce->hw_errors++; return false; } if ((!strncasecmp(pdevbuf, "TEMP", 4)) && (s = strchr(pdevbuf + 4, ':'))) { float temp = strtof(s + 1, NULL); /* Cope with older software that breaks and reads nonsense * values */ if (temp > 100) temp = strtod(s + 1, NULL); if (temp > 0) { bitforce->temp = temp; if (unlikely(bitforce->cutofftemp > 0 && temp > bitforce->cutofftemp)) { applog(LOG_WARNING, "BFL%i: Hit thermal cutoff limit, disabling!", bitforce->device_id); bitforce->deven = DEV_RECOVER; dev_error(bitforce, REASON_DEV_THERMAL_CUTOFF); } } } else { /* Use the temperature monitor as a kind of watchdog for when * our responses are out of sync and flush the buffer to * hopefully recover */ applog(LOG_WARNING, "BFL%i: Garbled response probably throttling, clearing buffer", bitforce->device_id); dev_error(bitforce, REASON_DEV_THROTTLE); /* Count throttling episodes as hardware errors */ bitforce->hw_errors++; bitforce_clear_buffer(bitforce); return false; } return true; }
static bool bitforce_get_temp(struct cgpu_info *bitforce) { char buf[BITFORCE_BUFSIZ+1]; int err, amount; char *s; /* Do not try to get the temperature if we're polling for a result to * minimise the chance of interleaved results */ if (bitforce->polling) return true; // Flash instead of Temp - doing both can be too slow if (bitforce->flash_led) { bitforce_flash_led(bitforce); return true; } /* It is not critical getting temperature so don't get stuck if we * can't grab the mutex here */ if (mutex_trylock(&bitforce->device_mutex)) return false; if ((err = usb_write(bitforce, BITFORCE_TEMPERATURE, BITFORCE_TEMPERATURE_LEN, &amount, C_REQUESTTEMPERATURE)) < 0 || amount != BITFORCE_TEMPERATURE_LEN) { mutex_unlock(&bitforce->device_mutex); applog(LOG_ERR, "%s%i: Error: Request temp invalid/timed out (%d:%d)", bitforce->drv->name, bitforce->device_id, amount, err); bitforce->hw_errors++; return false; } if ((err = usb_ftdi_read_nl(bitforce, buf, sizeof(buf)-1, &amount, C_GETTEMPERATURE)) < 0 || amount < 1) { mutex_unlock(&bitforce->device_mutex); if (err < 0) { applog(LOG_ERR, "%s%i: Error: Get temp return invalid/timed out (%d:%d)", bitforce->drv->name, bitforce->device_id, amount, err); } else { applog(LOG_ERR, "%s%i: Error: Get temp returned nothing (%d:%d)", bitforce->drv->name, bitforce->device_id, amount, err); } bitforce->hw_errors++; return false; } mutex_unlock(&bitforce->device_mutex); if ((!strncasecmp(buf, "TEMP", 4)) && (s = strchr(buf + 4, ':'))) { float temp = strtof(s + 1, NULL); /* Cope with older software that breaks and reads nonsense * values */ if (temp > 100) temp = strtod(s + 1, NULL); if (temp > 0) { bitforce->temp = temp; if (unlikely(bitforce->cutofftemp > 0 && temp > bitforce->cutofftemp)) { applog(LOG_WARNING, "%s%i: Hit thermal cutoff limit, disabling!", bitforce->drv->name, bitforce->device_id); bitforce->deven = DEV_RECOVER; dev_error(bitforce, REASON_DEV_THERMAL_CUTOFF); } } } else { /* Use the temperature monitor as a kind of watchdog for when * our responses are out of sync and flush the buffer to * hopefully recover */ applog(LOG_WARNING, "%s%i: Garbled response probably throttling, clearing buffer", bitforce->drv->name, bitforce->device_id); dev_error(bitforce, REASON_DEV_THROTTLE); /* Count throttling episodes as hardware errors */ bitforce->hw_errors++; bitforce_initialise(bitforce, true); return false; } return true; }