1 // SPDX-License-Identifier: GPL-2.0-only 2 /* 3 * Battery and Power Management code for the Sharp SL-C7xx and SL-Cxx00 4 * series of PDAs 5 * 6 * Copyright (c) 2004-2005 Richard Purdie 7 * 8 * Based on code written by Sharp for 2.4 kernels 9 */ 10 11 #undef DEBUG 12 13 #include <linux/module.h> 14 #include <linux/kernel.h> 15 #include <linux/interrupt.h> 16 #include <linux/platform_device.h> 17 #include <linux/apm-emulation.h> 18 #include <linux/timer.h> 19 #include <linux/delay.h> 20 #include <linux/leds.h> 21 #include <linux/suspend.h> 22 #include <linux/gpio.h> 23 #include <linux/io.h> 24 25 #include <asm/mach-types.h> 26 #include "pm.h" 27 #include "pxa2xx-regs.h" 28 #include "regs-rtc.h" 29 #include "sharpsl_pm.h" 30 31 /* 32 * Constants 33 */ 34 #define SHARPSL_CHARGE_ON_TIME_INTERVAL (msecs_to_jiffies(1*60*1000)) /* 1 min */ 35 #define SHARPSL_CHARGE_FINISH_TIME (msecs_to_jiffies(10*60*1000)) /* 10 min */ 36 #define SHARPSL_BATCHK_TIME (msecs_to_jiffies(15*1000)) /* 15 sec */ 37 #define SHARPSL_BATCHK_TIME_SUSPEND (60*10) /* 10 min */ 38 39 #define SHARPSL_WAIT_CO_TIME 15 /* 15 sec */ 40 #define SHARPSL_WAIT_DISCHARGE_ON 100 /* 100 msec */ 41 #define SHARPSL_CHECK_BATTERY_WAIT_TIME_TEMP 10 /* 10 msec */ 42 #define SHARPSL_CHECK_BATTERY_WAIT_TIME_VOLT 10 /* 10 msec */ 43 #define SHARPSL_CHECK_BATTERY_WAIT_TIME_ACIN 10 /* 10 msec */ 44 #define SHARPSL_CHARGE_WAIT_TIME 15 /* 15 msec */ 45 #define SHARPSL_CHARGE_CO_CHECK_TIME 5 /* 5 msec */ 46 #define SHARPSL_CHARGE_RETRY_CNT 1 /* eqv. 10 min */ 47 48 /* 49 * Prototypes 50 */ 51 #ifdef CONFIG_PM 52 static int sharpsl_off_charge_battery(void); 53 static int sharpsl_check_battery_voltage(void); 54 #endif 55 static int sharpsl_check_battery_temp(void); 56 static int sharpsl_ac_check(void); 57 static int sharpsl_average_value(int ad); 58 static void sharpsl_average_clear(void); 59 static void sharpsl_charge_toggle(struct work_struct *private_); 60 static void sharpsl_battery_thread(struct work_struct *private_); 61 62 63 /* 64 * Variables 65 */ 66 struct sharpsl_pm_status sharpsl_pm; 67 static DECLARE_DELAYED_WORK(toggle_charger, sharpsl_charge_toggle); 68 static DECLARE_DELAYED_WORK(sharpsl_bat, sharpsl_battery_thread); 69 DEFINE_LED_TRIGGER(sharpsl_charge_led_trigger); 70 71 72 73 struct battery_thresh sharpsl_battery_levels_acin[] = { 74 { 213, 100}, 75 { 212, 98}, 76 { 211, 95}, 77 { 210, 93}, 78 { 209, 90}, 79 { 208, 88}, 80 { 207, 85}, 81 { 206, 83}, 82 { 205, 80}, 83 { 204, 78}, 84 { 203, 75}, 85 { 202, 73}, 86 { 201, 70}, 87 { 200, 68}, 88 { 199, 65}, 89 { 198, 63}, 90 { 197, 60}, 91 { 196, 58}, 92 { 195, 55}, 93 { 194, 53}, 94 { 193, 50}, 95 { 192, 48}, 96 { 192, 45}, 97 { 191, 43}, 98 { 191, 40}, 99 { 190, 38}, 100 { 190, 35}, 101 { 189, 33}, 102 { 188, 30}, 103 { 187, 28}, 104 { 186, 25}, 105 { 185, 23}, 106 { 184, 20}, 107 { 183, 18}, 108 { 182, 15}, 109 { 181, 13}, 110 { 180, 10}, 111 { 179, 8}, 112 { 178, 5}, 113 { 0, 0}, 114 }; 115 116 struct battery_thresh sharpsl_battery_levels_noac[] = { 117 { 213, 100}, 118 { 212, 98}, 119 { 211, 95}, 120 { 210, 93}, 121 { 209, 90}, 122 { 208, 88}, 123 { 207, 85}, 124 { 206, 83}, 125 { 205, 80}, 126 { 204, 78}, 127 { 203, 75}, 128 { 202, 73}, 129 { 201, 70}, 130 { 200, 68}, 131 { 199, 65}, 132 { 198, 63}, 133 { 197, 60}, 134 { 196, 58}, 135 { 195, 55}, 136 { 194, 53}, 137 { 193, 50}, 138 { 192, 48}, 139 { 191, 45}, 140 { 190, 43}, 141 { 189, 40}, 142 { 188, 38}, 143 { 187, 35}, 144 { 186, 33}, 145 { 185, 30}, 146 { 184, 28}, 147 { 183, 25}, 148 { 182, 23}, 149 { 181, 20}, 150 { 180, 18}, 151 { 179, 15}, 152 { 178, 13}, 153 { 177, 10}, 154 { 176, 8}, 155 { 175, 5}, 156 { 0, 0}, 157 }; 158 159 /* MAX1111 Commands */ 160 #define MAXCTRL_PD0 (1u << 0) 161 #define MAXCTRL_PD1 (1u << 1) 162 #define MAXCTRL_SGL (1u << 2) 163 #define MAXCTRL_UNI (1u << 3) 164 #define MAXCTRL_SEL_SH 4 165 #define MAXCTRL_STR (1u << 7) 166 167 extern int max1111_read_channel(int); 168 /* 169 * Read MAX1111 ADC 170 */ 171 int sharpsl_pm_pxa_read_max1111(int channel) 172 { 173 /* max1111 accepts channels from 0-3, however, 174 * it is encoded from 0-7 here in the code. 175 */ 176 return max1111_read_channel(channel >> 1); 177 } 178 179 static int get_percentage(int voltage) 180 { 181 int i = sharpsl_pm.machinfo->bat_levels - 1; 182 int bl_status = sharpsl_pm.machinfo->backlight_get_status ? sharpsl_pm.machinfo->backlight_get_status() : 0; 183 struct battery_thresh *thresh; 184 185 if (sharpsl_pm.charge_mode == CHRG_ON) 186 thresh = bl_status ? sharpsl_pm.machinfo->bat_levels_acin_bl : sharpsl_pm.machinfo->bat_levels_acin; 187 else 188 thresh = bl_status ? sharpsl_pm.machinfo->bat_levels_noac_bl : sharpsl_pm.machinfo->bat_levels_noac; 189 190 while (i > 0 && (voltage > thresh[i].voltage)) 191 i--; 192 193 return thresh[i].percentage; 194 } 195 196 static int get_apm_status(int voltage) 197 { 198 int low_thresh, high_thresh; 199 200 if (sharpsl_pm.charge_mode == CHRG_ON) { 201 high_thresh = sharpsl_pm.machinfo->status_high_acin; 202 low_thresh = sharpsl_pm.machinfo->status_low_acin; 203 } else { 204 high_thresh = sharpsl_pm.machinfo->status_high_noac; 205 low_thresh = sharpsl_pm.machinfo->status_low_noac; 206 } 207 208 if (voltage >= high_thresh) 209 return APM_BATTERY_STATUS_HIGH; 210 if (voltage >= low_thresh) 211 return APM_BATTERY_STATUS_LOW; 212 return APM_BATTERY_STATUS_CRITICAL; 213 } 214 215 void sharpsl_battery_kick(void) 216 { 217 schedule_delayed_work(&sharpsl_bat, msecs_to_jiffies(125)); 218 } 219 EXPORT_SYMBOL(sharpsl_battery_kick); 220 221 222 static void sharpsl_battery_thread(struct work_struct *private_) 223 { 224 int voltage, percent, apm_status, i; 225 226 if (!sharpsl_pm.machinfo) 227 return; 228 229 sharpsl_pm.battstat.ac_status = (sharpsl_pm.machinfo->read_devdata(SHARPSL_STATUS_ACIN) ? APM_AC_ONLINE : APM_AC_OFFLINE); 230 231 /* Corgi cannot confirm when battery fully charged so periodically kick! */ 232 if (!sharpsl_pm.machinfo->batfull_irq && (sharpsl_pm.charge_mode == CHRG_ON) 233 && time_after(jiffies, sharpsl_pm.charge_start_time + SHARPSL_CHARGE_ON_TIME_INTERVAL)) 234 schedule_delayed_work(&toggle_charger, 0); 235 236 for (i = 0; i < 5; i++) { 237 voltage = sharpsl_pm.machinfo->read_devdata(SHARPSL_BATT_VOLT); 238 if (voltage > 0) 239 break; 240 } 241 if (voltage <= 0) { 242 voltage = sharpsl_pm.machinfo->bat_levels_noac[0].voltage; 243 dev_warn(sharpsl_pm.dev, "Warning: Cannot read main battery!\n"); 244 } 245 246 voltage = sharpsl_average_value(voltage); 247 apm_status = get_apm_status(voltage); 248 percent = get_percentage(voltage); 249 250 /* At low battery voltages, the voltage has a tendency to start 251 creeping back up so we try to avoid this here */ 252 if ((sharpsl_pm.battstat.ac_status == APM_AC_ONLINE) 253 || (apm_status == APM_BATTERY_STATUS_HIGH) 254 || percent <= sharpsl_pm.battstat.mainbat_percent) { 255 sharpsl_pm.battstat.mainbat_voltage = voltage; 256 sharpsl_pm.battstat.mainbat_status = apm_status; 257 sharpsl_pm.battstat.mainbat_percent = percent; 258 } 259 260 dev_dbg(sharpsl_pm.dev, "Battery: voltage: %d, status: %d, percentage: %d, time: %ld\n", voltage, 261 sharpsl_pm.battstat.mainbat_status, sharpsl_pm.battstat.mainbat_percent, jiffies); 262 263 /* Suspend if critical battery level */ 264 if ((sharpsl_pm.battstat.ac_status != APM_AC_ONLINE) 265 && (sharpsl_pm.battstat.mainbat_status == APM_BATTERY_STATUS_CRITICAL) 266 && !(sharpsl_pm.flags & SHARPSL_APM_QUEUED)) { 267 sharpsl_pm.flags |= SHARPSL_APM_QUEUED; 268 dev_err(sharpsl_pm.dev, "Fatal Off\n"); 269 apm_queue_event(APM_CRITICAL_SUSPEND); 270 } 271 272 schedule_delayed_work(&sharpsl_bat, SHARPSL_BATCHK_TIME); 273 } 274 275 void sharpsl_pm_led(int val) 276 { 277 if (val == SHARPSL_LED_ERROR) { 278 dev_err(sharpsl_pm.dev, "Charging Error!\n"); 279 } else if (val == SHARPSL_LED_ON) { 280 dev_dbg(sharpsl_pm.dev, "Charge LED On\n"); 281 led_trigger_event(sharpsl_charge_led_trigger, LED_FULL); 282 } else { 283 dev_dbg(sharpsl_pm.dev, "Charge LED Off\n"); 284 led_trigger_event(sharpsl_charge_led_trigger, LED_OFF); 285 } 286 } 287 288 static void sharpsl_charge_on(void) 289 { 290 dev_dbg(sharpsl_pm.dev, "Turning Charger On\n"); 291 292 sharpsl_pm.full_count = 0; 293 sharpsl_pm.charge_mode = CHRG_ON; 294 schedule_delayed_work(&toggle_charger, msecs_to_jiffies(250)); 295 schedule_delayed_work(&sharpsl_bat, msecs_to_jiffies(500)); 296 } 297 298 static void sharpsl_charge_off(void) 299 { 300 dev_dbg(sharpsl_pm.dev, "Turning Charger Off\n"); 301 302 sharpsl_pm.machinfo->charge(0); 303 sharpsl_pm_led(SHARPSL_LED_OFF); 304 sharpsl_pm.charge_mode = CHRG_OFF; 305 306 schedule_delayed_work(&sharpsl_bat, 0); 307 } 308 309 static void sharpsl_charge_error(void) 310 { 311 sharpsl_pm_led(SHARPSL_LED_ERROR); 312 sharpsl_pm.machinfo->charge(0); 313 sharpsl_pm.charge_mode = CHRG_ERROR; 314 } 315 316 static void sharpsl_charge_toggle(struct work_struct *private_) 317 { 318 dev_dbg(sharpsl_pm.dev, "Toggling Charger at time: %lx\n", jiffies); 319 320 if (!sharpsl_pm.machinfo->read_devdata(SHARPSL_STATUS_ACIN)) { 321 sharpsl_charge_off(); 322 return; 323 } else if ((sharpsl_check_battery_temp() < 0) || (sharpsl_ac_check() < 0)) { 324 sharpsl_charge_error(); 325 return; 326 } 327 328 sharpsl_pm_led(SHARPSL_LED_ON); 329 sharpsl_pm.machinfo->charge(0); 330 mdelay(SHARPSL_CHARGE_WAIT_TIME); 331 sharpsl_pm.machinfo->charge(1); 332 333 sharpsl_pm.charge_start_time = jiffies; 334 } 335 336 static void sharpsl_ac_timer(struct timer_list *unused) 337 { 338 int acin = sharpsl_pm.machinfo->read_devdata(SHARPSL_STATUS_ACIN); 339 340 dev_dbg(sharpsl_pm.dev, "AC Status: %d\n", acin); 341 342 sharpsl_average_clear(); 343 if (acin && (sharpsl_pm.charge_mode != CHRG_ON)) 344 sharpsl_charge_on(); 345 else if (sharpsl_pm.charge_mode == CHRG_ON) 346 sharpsl_charge_off(); 347 348 schedule_delayed_work(&sharpsl_bat, 0); 349 } 350 351 352 static irqreturn_t sharpsl_ac_isr(int irq, void *dev_id) 353 { 354 /* Delay the event slightly to debounce */ 355 /* Must be a smaller delay than the chrg_full_isr below */ 356 mod_timer(&sharpsl_pm.ac_timer, jiffies + msecs_to_jiffies(250)); 357 358 return IRQ_HANDLED; 359 } 360 361 static void sharpsl_chrg_full_timer(struct timer_list *unused) 362 { 363 dev_dbg(sharpsl_pm.dev, "Charge Full at time: %lx\n", jiffies); 364 365 sharpsl_pm.full_count++; 366 367 if (!sharpsl_pm.machinfo->read_devdata(SHARPSL_STATUS_ACIN)) { 368 dev_dbg(sharpsl_pm.dev, "Charge Full: AC removed - stop charging!\n"); 369 if (sharpsl_pm.charge_mode == CHRG_ON) 370 sharpsl_charge_off(); 371 } else if (sharpsl_pm.full_count < 2) { 372 dev_dbg(sharpsl_pm.dev, "Charge Full: Count too low\n"); 373 schedule_delayed_work(&toggle_charger, 0); 374 } else if (time_after(jiffies, sharpsl_pm.charge_start_time + SHARPSL_CHARGE_FINISH_TIME)) { 375 dev_dbg(sharpsl_pm.dev, "Charge Full: Interrupt generated too slowly - retry.\n"); 376 schedule_delayed_work(&toggle_charger, 0); 377 } else { 378 sharpsl_charge_off(); 379 sharpsl_pm.charge_mode = CHRG_DONE; 380 dev_dbg(sharpsl_pm.dev, "Charge Full: Charging Finished\n"); 381 } 382 } 383 384 /* Charging Finished Interrupt (Not present on Corgi) */ 385 /* Can trigger at the same time as an AC status change so 386 delay until after that has been processed */ 387 static irqreturn_t sharpsl_chrg_full_isr(int irq, void *dev_id) 388 { 389 if (sharpsl_pm.flags & SHARPSL_SUSPENDED) 390 return IRQ_HANDLED; 391 392 /* delay until after any ac interrupt */ 393 mod_timer(&sharpsl_pm.chrg_full_timer, jiffies + msecs_to_jiffies(500)); 394 395 return IRQ_HANDLED; 396 } 397 398 static irqreturn_t sharpsl_fatal_isr(int irq, void *dev_id) 399 { 400 int is_fatal = 0; 401 402 if (!sharpsl_pm.machinfo->read_devdata(SHARPSL_STATUS_LOCK)) { 403 dev_err(sharpsl_pm.dev, "Battery now Unlocked! Suspending.\n"); 404 is_fatal = 1; 405 } 406 407 if (!sharpsl_pm.machinfo->read_devdata(SHARPSL_STATUS_FATAL)) { 408 dev_err(sharpsl_pm.dev, "Fatal Batt Error! Suspending.\n"); 409 is_fatal = 1; 410 } 411 412 if (!(sharpsl_pm.flags & SHARPSL_APM_QUEUED) && is_fatal) { 413 sharpsl_pm.flags |= SHARPSL_APM_QUEUED; 414 apm_queue_event(APM_CRITICAL_SUSPEND); 415 } 416 417 return IRQ_HANDLED; 418 } 419 420 /* 421 * Maintain an average of the last 10 readings 422 */ 423 #define SHARPSL_CNV_VALUE_NUM 10 424 static int sharpsl_ad_index; 425 426 static void sharpsl_average_clear(void) 427 { 428 sharpsl_ad_index = 0; 429 } 430 431 static int sharpsl_average_value(int ad) 432 { 433 int i, ad_val = 0; 434 static int sharpsl_ad[SHARPSL_CNV_VALUE_NUM+1]; 435 436 if (sharpsl_pm.battstat.mainbat_status != APM_BATTERY_STATUS_HIGH) { 437 sharpsl_ad_index = 0; 438 return ad; 439 } 440 441 sharpsl_ad[sharpsl_ad_index] = ad; 442 sharpsl_ad_index++; 443 if (sharpsl_ad_index >= SHARPSL_CNV_VALUE_NUM) { 444 for (i = 0; i < (SHARPSL_CNV_VALUE_NUM-1); i++) 445 sharpsl_ad[i] = sharpsl_ad[i+1]; 446 sharpsl_ad_index = SHARPSL_CNV_VALUE_NUM - 1; 447 } 448 for (i = 0; i < sharpsl_ad_index; i++) 449 ad_val += sharpsl_ad[i]; 450 451 return ad_val / sharpsl_ad_index; 452 } 453 454 /* 455 * Take an array of 5 integers, remove the maximum and minimum values 456 * and return the average. 457 */ 458 static int get_select_val(int *val) 459 { 460 int i, j, k, temp, sum = 0; 461 462 /* Find MAX val */ 463 temp = val[0]; 464 j = 0; 465 for (i = 1; i < 5; i++) { 466 if (temp < val[i]) { 467 temp = val[i]; 468 j = i; 469 } 470 } 471 472 /* Find MIN val */ 473 temp = val[4]; 474 k = 4; 475 for (i = 3; i >= 0; i--) { 476 if (temp > val[i]) { 477 temp = val[i]; 478 k = i; 479 } 480 } 481 482 for (i = 0; i < 5; i++) 483 if (i != j && i != k) 484 sum += val[i]; 485 486 dev_dbg(sharpsl_pm.dev, "Average: %d from values: %d, %d, %d, %d, %d\n", sum/3, val[0], val[1], val[2], val[3], val[4]); 487 488 return sum/3; 489 } 490 491 static int sharpsl_check_battery_temp(void) 492 { 493 int val, i, buff[5]; 494 495 /* Check battery temperature */ 496 for (i = 0; i < 5; i++) { 497 mdelay(SHARPSL_CHECK_BATTERY_WAIT_TIME_TEMP); 498 sharpsl_pm.machinfo->measure_temp(1); 499 mdelay(SHARPSL_CHECK_BATTERY_WAIT_TIME_TEMP); 500 buff[i] = sharpsl_pm.machinfo->read_devdata(SHARPSL_BATT_TEMP); 501 sharpsl_pm.machinfo->measure_temp(0); 502 } 503 504 val = get_select_val(buff); 505 506 dev_dbg(sharpsl_pm.dev, "Temperature: %d\n", val); 507 if (val > sharpsl_pm.machinfo->charge_on_temp) { 508 printk(KERN_WARNING "Not charging: temperature out of limits.\n"); 509 return -1; 510 } 511 512 return 0; 513 } 514 515 #ifdef CONFIG_PM 516 static int sharpsl_check_battery_voltage(void) 517 { 518 int val, i, buff[5]; 519 520 /* disable charge, enable discharge */ 521 sharpsl_pm.machinfo->charge(0); 522 sharpsl_pm.machinfo->discharge(1); 523 mdelay(SHARPSL_WAIT_DISCHARGE_ON); 524 525 if (sharpsl_pm.machinfo->discharge1) 526 sharpsl_pm.machinfo->discharge1(1); 527 528 /* Check battery voltage */ 529 for (i = 0; i < 5; i++) { 530 buff[i] = sharpsl_pm.machinfo->read_devdata(SHARPSL_BATT_VOLT); 531 mdelay(SHARPSL_CHECK_BATTERY_WAIT_TIME_VOLT); 532 } 533 534 if (sharpsl_pm.machinfo->discharge1) 535 sharpsl_pm.machinfo->discharge1(0); 536 537 sharpsl_pm.machinfo->discharge(0); 538 539 val = get_select_val(buff); 540 dev_dbg(sharpsl_pm.dev, "Battery Voltage: %d\n", val); 541 542 if (val < sharpsl_pm.machinfo->charge_on_volt) 543 return -1; 544 545 return 0; 546 } 547 #endif 548 549 static int sharpsl_ac_check(void) 550 { 551 int temp, i, buff[5]; 552 553 for (i = 0; i < 5; i++) { 554 buff[i] = sharpsl_pm.machinfo->read_devdata(SHARPSL_ACIN_VOLT); 555 mdelay(SHARPSL_CHECK_BATTERY_WAIT_TIME_ACIN); 556 } 557 558 temp = get_select_val(buff); 559 dev_dbg(sharpsl_pm.dev, "AC Voltage: %d\n", temp); 560 561 if ((temp > sharpsl_pm.machinfo->charge_acin_high) || (temp < sharpsl_pm.machinfo->charge_acin_low)) { 562 dev_err(sharpsl_pm.dev, "Error: AC check failed: voltage %d.\n", temp); 563 return -1; 564 } 565 566 return 0; 567 } 568 569 #ifdef CONFIG_PM 570 static int sharpsl_pm_suspend(struct platform_device *pdev, pm_message_t state) 571 { 572 sharpsl_pm.flags |= SHARPSL_SUSPENDED; 573 flush_delayed_work(&toggle_charger); 574 flush_delayed_work(&sharpsl_bat); 575 576 if (sharpsl_pm.charge_mode == CHRG_ON) 577 sharpsl_pm.flags |= SHARPSL_DO_OFFLINE_CHRG; 578 else 579 sharpsl_pm.flags &= ~SHARPSL_DO_OFFLINE_CHRG; 580 581 return 0; 582 } 583 584 static int sharpsl_pm_resume(struct platform_device *pdev) 585 { 586 /* Clear the reset source indicators as they break the bootloader upon reboot */ 587 RCSR = 0x0f; 588 sharpsl_average_clear(); 589 sharpsl_pm.flags &= ~SHARPSL_APM_QUEUED; 590 sharpsl_pm.flags &= ~SHARPSL_SUSPENDED; 591 592 return 0; 593 } 594 595 static void corgi_goto_sleep(unsigned long alarm_time, unsigned int alarm_enable, suspend_state_t state) 596 { 597 dev_dbg(sharpsl_pm.dev, "Time is: %08x\n", RCNR); 598 599 dev_dbg(sharpsl_pm.dev, "Offline Charge Activate = %d\n", sharpsl_pm.flags & SHARPSL_DO_OFFLINE_CHRG); 600 /* not charging and AC-IN! */ 601 602 if ((sharpsl_pm.flags & SHARPSL_DO_OFFLINE_CHRG) && (sharpsl_pm.machinfo->read_devdata(SHARPSL_STATUS_ACIN))) { 603 dev_dbg(sharpsl_pm.dev, "Activating Offline Charger...\n"); 604 sharpsl_pm.charge_mode = CHRG_OFF; 605 sharpsl_pm.flags &= ~SHARPSL_DO_OFFLINE_CHRG; 606 sharpsl_off_charge_battery(); 607 } 608 609 sharpsl_pm.machinfo->presuspend(); 610 611 PEDR = 0xffffffff; /* clear it */ 612 613 sharpsl_pm.flags &= ~SHARPSL_ALARM_ACTIVE; 614 if ((sharpsl_pm.charge_mode == CHRG_ON) && ((alarm_enable && ((alarm_time - RCNR) > (SHARPSL_BATCHK_TIME_SUSPEND + 30))) || !alarm_enable)) { 615 RTSR &= RTSR_ALE; 616 RTAR = RCNR + SHARPSL_BATCHK_TIME_SUSPEND; 617 dev_dbg(sharpsl_pm.dev, "Charging alarm at: %08x\n", RTAR); 618 sharpsl_pm.flags |= SHARPSL_ALARM_ACTIVE; 619 } else if (alarm_enable) { 620 RTSR &= RTSR_ALE; 621 RTAR = alarm_time; 622 dev_dbg(sharpsl_pm.dev, "User alarm at: %08x\n", RTAR); 623 } else { 624 dev_dbg(sharpsl_pm.dev, "No alarms set.\n"); 625 } 626 627 pxa_pm_enter(state); 628 629 sharpsl_pm.machinfo->postsuspend(); 630 631 dev_dbg(sharpsl_pm.dev, "Corgi woken up from suspend: %08x\n", PEDR); 632 } 633 634 static int corgi_enter_suspend(unsigned long alarm_time, unsigned int alarm_enable, suspend_state_t state) 635 { 636 if (!sharpsl_pm.machinfo->should_wakeup(!(sharpsl_pm.flags & SHARPSL_ALARM_ACTIVE) && alarm_enable)) { 637 if (!(sharpsl_pm.flags & SHARPSL_ALARM_ACTIVE)) { 638 dev_dbg(sharpsl_pm.dev, "No user triggered wakeup events and not charging. Strange. Suspend.\n"); 639 corgi_goto_sleep(alarm_time, alarm_enable, state); 640 return 1; 641 } 642 if (sharpsl_off_charge_battery()) { 643 dev_dbg(sharpsl_pm.dev, "Charging. Suspend...\n"); 644 corgi_goto_sleep(alarm_time, alarm_enable, state); 645 return 1; 646 } 647 dev_dbg(sharpsl_pm.dev, "User triggered wakeup in offline charger.\n"); 648 } 649 650 if ((!sharpsl_pm.machinfo->read_devdata(SHARPSL_STATUS_LOCK)) || 651 (!sharpsl_pm.machinfo->read_devdata(SHARPSL_STATUS_FATAL))) { 652 dev_err(sharpsl_pm.dev, "Fatal condition. Suspend.\n"); 653 corgi_goto_sleep(alarm_time, alarm_enable, state); 654 return 1; 655 } 656 657 return 0; 658 } 659 660 static int corgi_pxa_pm_enter(suspend_state_t state) 661 { 662 unsigned long alarm_time = RTAR; 663 unsigned int alarm_status = ((RTSR & RTSR_ALE) != 0); 664 665 dev_dbg(sharpsl_pm.dev, "SharpSL suspending for first time.\n"); 666 667 corgi_goto_sleep(alarm_time, alarm_status, state); 668 669 while (corgi_enter_suspend(alarm_time, alarm_status, state)) 670 {} 671 672 if (sharpsl_pm.machinfo->earlyresume) 673 sharpsl_pm.machinfo->earlyresume(); 674 675 dev_dbg(sharpsl_pm.dev, "SharpSL resuming...\n"); 676 677 return 0; 678 } 679 680 static int sharpsl_off_charge_error(void) 681 { 682 dev_err(sharpsl_pm.dev, "Offline Charger: Error occurred.\n"); 683 sharpsl_pm.machinfo->charge(0); 684 sharpsl_pm_led(SHARPSL_LED_ERROR); 685 sharpsl_pm.charge_mode = CHRG_ERROR; 686 return 1; 687 } 688 689 /* 690 * Charging Control while suspended 691 * Return 1 - go straight to sleep 692 * Return 0 - sleep or wakeup depending on other factors 693 */ 694 static int sharpsl_off_charge_battery(void) 695 { 696 int time; 697 698 dev_dbg(sharpsl_pm.dev, "Charge Mode: %d\n", sharpsl_pm.charge_mode); 699 700 if (sharpsl_pm.charge_mode == CHRG_OFF) { 701 dev_dbg(sharpsl_pm.dev, "Offline Charger: Step 1\n"); 702 703 /* AC Check */ 704 if ((sharpsl_ac_check() < 0) || (sharpsl_check_battery_temp() < 0)) 705 return sharpsl_off_charge_error(); 706 707 /* Start Charging */ 708 sharpsl_pm_led(SHARPSL_LED_ON); 709 sharpsl_pm.machinfo->charge(0); 710 mdelay(SHARPSL_CHARGE_WAIT_TIME); 711 sharpsl_pm.machinfo->charge(1); 712 713 sharpsl_pm.charge_mode = CHRG_ON; 714 sharpsl_pm.full_count = 0; 715 716 return 1; 717 } else if (sharpsl_pm.charge_mode != CHRG_ON) { 718 return 1; 719 } 720 721 if (sharpsl_pm.full_count == 0) { 722 int time; 723 724 dev_dbg(sharpsl_pm.dev, "Offline Charger: Step 2\n"); 725 726 if ((sharpsl_check_battery_temp() < 0) || (sharpsl_check_battery_voltage() < 0)) 727 return sharpsl_off_charge_error(); 728 729 sharpsl_pm.machinfo->charge(0); 730 mdelay(SHARPSL_CHARGE_WAIT_TIME); 731 sharpsl_pm.machinfo->charge(1); 732 sharpsl_pm.charge_mode = CHRG_ON; 733 734 mdelay(SHARPSL_CHARGE_CO_CHECK_TIME); 735 736 time = RCNR; 737 while (1) { 738 /* Check if any wakeup event had occurred */ 739 if (sharpsl_pm.machinfo->charger_wakeup()) 740 return 0; 741 /* Check for timeout */ 742 if ((RCNR - time) > SHARPSL_WAIT_CO_TIME) 743 return 1; 744 if (sharpsl_pm.machinfo->read_devdata(SHARPSL_STATUS_CHRGFULL)) { 745 dev_dbg(sharpsl_pm.dev, "Offline Charger: Charge full occurred. Retrying to check\n"); 746 sharpsl_pm.full_count++; 747 sharpsl_pm.machinfo->charge(0); 748 mdelay(SHARPSL_CHARGE_WAIT_TIME); 749 sharpsl_pm.machinfo->charge(1); 750 return 1; 751 } 752 } 753 } 754 755 dev_dbg(sharpsl_pm.dev, "Offline Charger: Step 3\n"); 756 757 mdelay(SHARPSL_CHARGE_CO_CHECK_TIME); 758 759 time = RCNR; 760 while (1) { 761 /* Check if any wakeup event had occurred */ 762 if (sharpsl_pm.machinfo->charger_wakeup()) 763 return 0; 764 /* Check for timeout */ 765 if ((RCNR-time) > SHARPSL_WAIT_CO_TIME) { 766 if (sharpsl_pm.full_count > SHARPSL_CHARGE_RETRY_CNT) { 767 dev_dbg(sharpsl_pm.dev, "Offline Charger: Not charged sufficiently. Retrying.\n"); 768 sharpsl_pm.full_count = 0; 769 } 770 sharpsl_pm.full_count++; 771 return 1; 772 } 773 if (sharpsl_pm.machinfo->read_devdata(SHARPSL_STATUS_CHRGFULL)) { 774 dev_dbg(sharpsl_pm.dev, "Offline Charger: Charging complete.\n"); 775 sharpsl_pm_led(SHARPSL_LED_OFF); 776 sharpsl_pm.machinfo->charge(0); 777 sharpsl_pm.charge_mode = CHRG_DONE; 778 return 1; 779 } 780 } 781 } 782 #else 783 #define sharpsl_pm_suspend NULL 784 #define sharpsl_pm_resume NULL 785 #endif 786 787 static ssize_t battery_percentage_show(struct device *dev, struct device_attribute *attr, char *buf) 788 { 789 return sprintf(buf, "%d\n", sharpsl_pm.battstat.mainbat_percent); 790 } 791 792 static ssize_t battery_voltage_show(struct device *dev, struct device_attribute *attr, char *buf) 793 { 794 return sprintf(buf, "%d\n", sharpsl_pm.battstat.mainbat_voltage); 795 } 796 797 static DEVICE_ATTR_RO(battery_percentage); 798 static DEVICE_ATTR_RO(battery_voltage); 799 800 extern void (*apm_get_power_status)(struct apm_power_info *); 801 802 static void sharpsl_apm_get_power_status(struct apm_power_info *info) 803 { 804 info->ac_line_status = sharpsl_pm.battstat.ac_status; 805 806 if (sharpsl_pm.charge_mode == CHRG_ON) 807 info->battery_status = APM_BATTERY_STATUS_CHARGING; 808 else 809 info->battery_status = sharpsl_pm.battstat.mainbat_status; 810 811 info->battery_flag = (1 << info->battery_status); 812 info->battery_life = sharpsl_pm.battstat.mainbat_percent; 813 } 814 815 #ifdef CONFIG_PM 816 static const struct platform_suspend_ops sharpsl_pm_ops = { 817 .prepare = pxa_pm_prepare, 818 .finish = pxa_pm_finish, 819 .enter = corgi_pxa_pm_enter, 820 .valid = suspend_valid_only_mem, 821 }; 822 #endif 823 824 static int sharpsl_pm_probe(struct platform_device *pdev) 825 { 826 int ret, irq; 827 828 if (!pdev->dev.platform_data) 829 return -EINVAL; 830 831 sharpsl_pm.dev = &pdev->dev; 832 sharpsl_pm.machinfo = pdev->dev.platform_data; 833 sharpsl_pm.charge_mode = CHRG_OFF; 834 sharpsl_pm.flags = 0; 835 836 timer_setup(&sharpsl_pm.ac_timer, sharpsl_ac_timer, 0); 837 838 timer_setup(&sharpsl_pm.chrg_full_timer, sharpsl_chrg_full_timer, 0); 839 840 led_trigger_register_simple("sharpsl-charge", &sharpsl_charge_led_trigger); 841 842 sharpsl_pm.machinfo->init(); 843 844 gpio_request(sharpsl_pm.machinfo->gpio_acin, "AC IN"); 845 gpio_direction_input(sharpsl_pm.machinfo->gpio_acin); 846 gpio_request(sharpsl_pm.machinfo->gpio_batfull, "Battery Full"); 847 gpio_direction_input(sharpsl_pm.machinfo->gpio_batfull); 848 gpio_request(sharpsl_pm.machinfo->gpio_batlock, "Battery Lock"); 849 gpio_direction_input(sharpsl_pm.machinfo->gpio_batlock); 850 851 /* Register interrupt handlers */ 852 irq = gpio_to_irq(sharpsl_pm.machinfo->gpio_acin); 853 if (request_irq(irq, sharpsl_ac_isr, IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING, "AC Input Detect", sharpsl_ac_isr)) { 854 dev_err(sharpsl_pm.dev, "Could not get irq %d.\n", irq); 855 } 856 857 irq = gpio_to_irq(sharpsl_pm.machinfo->gpio_batlock); 858 if (request_irq(irq, sharpsl_fatal_isr, IRQF_TRIGGER_FALLING, "Battery Cover", sharpsl_fatal_isr)) { 859 dev_err(sharpsl_pm.dev, "Could not get irq %d.\n", irq); 860 } 861 862 if (sharpsl_pm.machinfo->gpio_fatal) { 863 irq = gpio_to_irq(sharpsl_pm.machinfo->gpio_fatal); 864 if (request_irq(irq, sharpsl_fatal_isr, IRQF_TRIGGER_FALLING, "Fatal Battery", sharpsl_fatal_isr)) { 865 dev_err(sharpsl_pm.dev, "Could not get irq %d.\n", irq); 866 } 867 } 868 869 if (sharpsl_pm.machinfo->batfull_irq) { 870 /* Register interrupt handler. */ 871 irq = gpio_to_irq(sharpsl_pm.machinfo->gpio_batfull); 872 if (request_irq(irq, sharpsl_chrg_full_isr, IRQF_TRIGGER_RISING, "CO", sharpsl_chrg_full_isr)) { 873 dev_err(sharpsl_pm.dev, "Could not get irq %d.\n", irq); 874 } 875 } 876 877 ret = device_create_file(&pdev->dev, &dev_attr_battery_percentage); 878 ret |= device_create_file(&pdev->dev, &dev_attr_battery_voltage); 879 if (ret != 0) 880 dev_warn(&pdev->dev, "Failed to register attributes (%d)\n", ret); 881 882 apm_get_power_status = sharpsl_apm_get_power_status; 883 884 #ifdef CONFIG_PM 885 suspend_set_ops(&sharpsl_pm_ops); 886 #endif 887 888 mod_timer(&sharpsl_pm.ac_timer, jiffies + msecs_to_jiffies(250)); 889 890 return 0; 891 } 892 893 static int sharpsl_pm_remove(struct platform_device *pdev) 894 { 895 suspend_set_ops(NULL); 896 897 device_remove_file(&pdev->dev, &dev_attr_battery_percentage); 898 device_remove_file(&pdev->dev, &dev_attr_battery_voltage); 899 900 led_trigger_unregister_simple(sharpsl_charge_led_trigger); 901 902 free_irq(gpio_to_irq(sharpsl_pm.machinfo->gpio_acin), sharpsl_ac_isr); 903 free_irq(gpio_to_irq(sharpsl_pm.machinfo->gpio_batlock), sharpsl_fatal_isr); 904 905 if (sharpsl_pm.machinfo->gpio_fatal) 906 free_irq(gpio_to_irq(sharpsl_pm.machinfo->gpio_fatal), sharpsl_fatal_isr); 907 908 if (sharpsl_pm.machinfo->batfull_irq) 909 free_irq(gpio_to_irq(sharpsl_pm.machinfo->gpio_batfull), sharpsl_chrg_full_isr); 910 911 gpio_free(sharpsl_pm.machinfo->gpio_batlock); 912 gpio_free(sharpsl_pm.machinfo->gpio_batfull); 913 gpio_free(sharpsl_pm.machinfo->gpio_acin); 914 915 if (sharpsl_pm.machinfo->exit) 916 sharpsl_pm.machinfo->exit(); 917 918 del_timer_sync(&sharpsl_pm.chrg_full_timer); 919 del_timer_sync(&sharpsl_pm.ac_timer); 920 921 return 0; 922 } 923 924 static struct platform_driver sharpsl_pm_driver = { 925 .probe = sharpsl_pm_probe, 926 .remove = sharpsl_pm_remove, 927 .suspend = sharpsl_pm_suspend, 928 .resume = sharpsl_pm_resume, 929 .driver = { 930 .name = "sharpsl-pm", 931 }, 932 }; 933 934 static int sharpsl_pm_init(void) 935 { 936 return platform_driver_register(&sharpsl_pm_driver); 937 } 938 939 static void sharpsl_pm_exit(void) 940 { 941 platform_driver_unregister(&sharpsl_pm_driver); 942 } 943 944 late_initcall(sharpsl_pm_init); 945 module_exit(sharpsl_pm_exit); 946