+}
+
+static void do_monitor_cpu_combined(void)
+{
+ struct cpu_pid_state *state0 = &cpu_state[0];
+ struct cpu_pid_state *state1 = &cpu_state[1];
+ s32 temp0, power0, temp1, power1;
+ s32 temp_combi, power_combi;
+ int rc, intake, pump;
+
+ rc = do_read_one_cpu_values(state0, &temp0, &power0);
+ if (rc < 0) {
+ /* XXX What do we do now ? */
+ }
+ state1->overtemp = 0;
+ rc = do_read_one_cpu_values(state1, &temp1, &power1);
+ if (rc < 0) {
+ /* XXX What do we do now ? */
+ }
+ if (state1->overtemp)
+ state0->overtemp++;
+
+ temp_combi = max(temp0, temp1);
+ power_combi = max(power0, power1);
+
+ /* Check tmax, increment overtemp if we are there. At tmax+8, we go
+ * full blown immediately and try to trigger a shutdown
+ */
+ if (temp_combi >= ((state0->mpu.tmax + 8) << 16)) {
+ printk(KERN_WARNING "Warning ! Temperature way above maximum (%d) !\n",
+ temp_combi >> 16);
+ state0->overtemp = CPU_MAX_OVERTEMP;
+ } else if (temp_combi > (state0->mpu.tmax << 16))
+ state0->overtemp++;
+ else
+ state0->overtemp = 0;
+ if (state0->overtemp >= CPU_MAX_OVERTEMP)
+ critical_state = 1;
+ if (state0->overtemp > 0) {
+ state0->rpm = state0->mpu.rmaxn_exhaust_fan;
+ state0->intake_rpm = intake = state0->mpu.rmaxn_intake_fan;
+ pump = CPU_PUMP_OUTPUT_MAX;
+ goto do_set_fans;
+ }
+
+ /* Do the PID */
+ do_cpu_pid(state0, temp_combi, power_combi);
+
+ /* Calculate intake fan speed */
+ intake = (state0->rpm * CPU_INTAKE_SCALE) >> 16;
+ if (intake < (int)state0->mpu.rminn_intake_fan)
+ intake = state0->mpu.rminn_intake_fan;
+ if (intake > (int)state0->mpu.rmaxn_intake_fan)
+ intake = state0->mpu.rmaxn_intake_fan;
+ state0->intake_rpm = intake;
+
+ /* Calculate pump speed */
+ pump = (state0->rpm * CPU_PUMP_OUTPUT_MAX) /
+ state0->mpu.rmaxn_exhaust_fan;
+ if (pump > CPU_PUMP_OUTPUT_MAX)
+ pump = CPU_PUMP_OUTPUT_MAX;
+ if (pump < CPU_PUMP_OUTPUT_MIN)
+ pump = CPU_PUMP_OUTPUT_MIN;
+
+ do_set_fans:
+ /* We copy values from state 0 to state 1 for /sysfs */
+ state1->rpm = state0->rpm;
+ state1->intake_rpm = state0->intake_rpm;
+
+ DBG("** CPU %d RPM: %d Ex, %d, Pump: %d, In, overtemp: %d\n",
+ state1->index, (int)state1->rpm, intake, pump, state1->overtemp);
+
+ /* We should check for errors, shouldn't we ? But then, what
+ * do we do once the error occurs ? For FCU notified fan
+ * failures (-EFAULT) we probably want to notify userland
+ * some way...
+ */
+ set_rpm_fan(CPUA_INTAKE_FAN_RPM_INDEX, intake);
+ set_rpm_fan(CPUA_EXHAUST_FAN_RPM_INDEX, state0->rpm);
+ set_rpm_fan(CPUB_INTAKE_FAN_RPM_INDEX, intake);
+ set_rpm_fan(CPUB_EXHAUST_FAN_RPM_INDEX, state0->rpm);
+
+ if (fcu_fans[CPUA_PUMP_RPM_INDEX].id != FCU_FAN_ABSENT_ID)
+ set_rpm_fan(CPUA_PUMP_RPM_INDEX, pump);
+ if (fcu_fans[CPUB_PUMP_RPM_INDEX].id != FCU_FAN_ABSENT_ID)
+ set_rpm_fan(CPUB_PUMP_RPM_INDEX, pump);
+}
+
+static void do_monitor_cpu_split(struct cpu_pid_state *state)
+{
+ s32 temp, power;
+ int rc, intake;
+
+ /* Read current fan status */
+ rc = do_read_one_cpu_values(state, &temp, &power);
+ if (rc < 0) {
+ /* XXX What do we do now ? */
+ }
+
+ /* Check tmax, increment overtemp if we are there. At tmax+8, we go
+ * full blown immediately and try to trigger a shutdown
+ */
+ if (temp >= ((state->mpu.tmax + 8) << 16)) {
+ printk(KERN_WARNING "Warning ! CPU %d temperature way above maximum"
+ " (%d) !\n",
+ state->index, temp >> 16);
+ state->overtemp = CPU_MAX_OVERTEMP;
+ } else if (temp > (state->mpu.tmax << 16))
+ state->overtemp++;
+ else
+ state->overtemp = 0;
+ if (state->overtemp >= CPU_MAX_OVERTEMP)
+ critical_state = 1;
+ if (state->overtemp > 0) {
+ state->rpm = state->mpu.rmaxn_exhaust_fan;
+ state->intake_rpm = intake = state->mpu.rmaxn_intake_fan;
+ goto do_set_fans;
+ }
+
+ /* Do the PID */
+ do_cpu_pid(state, temp, power);