aboutsummaryrefslogtreecommitdiffstats
path: root/arch/i386/kernel/cpu
diff options
context:
space:
mode:
authorrafalbilski@interia.pl <rafalbilski@interia.pl>2006-09-24 14:28:13 -0400
committerDave Jones <davej@redhat.com>2006-09-26 23:12:02 -0400
commit7f1be8924791535c5fdc6749d1f119e141baa122 (patch)
tree195e61a5bd40e3d01abc56f3355b04d34da0d476 /arch/i386/kernel/cpu
parent0497c8ca282915a1c36d51db33fbf2629d7346f3 (diff)
[CPUFREQ] Longhaul - Disable arbiter CLE266
Please ignore previous message. This patch is adding support for CPU connected to CLE266 chipset. For older CPU this is only way. For "Powersaver" processor this way will be used if ACPI C3 isn't supported. I have tested it. It seems to work exacly like ACPI. But it is less safe. On CLE266 chipset port 0x22 is blocking processor access to PCI bus too. Signed-off-by: Rafa³ Bilski <rafalbilski@interia.pl> Signed-off-by: Dave Jones <davej@redhat.com>
Diffstat (limited to 'arch/i386/kernel/cpu')
-rw-r--r--arch/i386/kernel/cpu/cpufreq/longhaul.c51
1 files changed, 37 insertions, 14 deletions
diff --git a/arch/i386/kernel/cpu/cpufreq/longhaul.c b/arch/i386/kernel/cpu/cpufreq/longhaul.c
index f5cc9f5c9bab..4e8dd743d00b 100644
--- a/arch/i386/kernel/cpu/cpufreq/longhaul.c
+++ b/arch/i386/kernel/cpu/cpufreq/longhaul.c
@@ -178,11 +178,17 @@ static void do_powersaver(int cx_address, unsigned int clock_ratio_index)
178 safe_halt(); 178 safe_halt();
179 /* Change frequency on next halt or sleep */ 179 /* Change frequency on next halt or sleep */
180 wrmsrl(MSR_VIA_LONGHAUL, longhaul.val); 180 wrmsrl(MSR_VIA_LONGHAUL, longhaul.val);
181 ACPI_FLUSH_CPU_CACHE(); 181 if (port22_en) {
182 /* Invoke C3 */ 182 ACPI_FLUSH_CPU_CACHE();
183 inb(cx_address); 183 /* Invoke C1 */
184 /* Dummy op - must do something useless after P_LVL3 read */ 184 halt();
185 t = inl(acpi_fadt.xpm_tmr_blk.address); 185 } else {
186 ACPI_FLUSH_CPU_CACHE();
187 /* Invoke C3 */
188 inb(cx_address);
189 /* Dummy op - must do something useless after P_LVL3 read */
190 t = inl(acpi_fadt.xpm_tmr_blk.address);
191 }
186 192
187 /* Disable bus ratio bit */ 193 /* Disable bus ratio bit */
188 local_irq_disable(); 194 local_irq_disable();
@@ -567,16 +573,23 @@ static acpi_status longhaul_walk_callback(acpi_handle obj_handle,
567static int enable_arbiter_disable(void) 573static int enable_arbiter_disable(void)
568{ 574{
569 struct pci_dev *dev; 575 struct pci_dev *dev;
576 int reg;
570 u8 pci_cmd; 577 u8 pci_cmd;
571 578
572 /* Find PLE133 host bridge */ 579 /* Find PLE133 host bridge */
580 reg = 0x78;
573 dev = pci_find_device(PCI_VENDOR_ID_VIA, PCI_DEVICE_ID_VIA_8601_0, NULL); 581 dev = pci_find_device(PCI_VENDOR_ID_VIA, PCI_DEVICE_ID_VIA_8601_0, NULL);
582 /* Find CLE266 host bridge */
583 if (dev == NULL) {
584 dev = pci_find_device(PCI_VENDOR_ID_VIA, PCI_DEVICE_ID_VIA_862X_0, NULL);
585 reg = 0x76;
586 }
574 if (dev != NULL) { 587 if (dev != NULL) {
575 /* Enable access to port 0x22 */ 588 /* Enable access to port 0x22 */
576 pci_read_config_byte(dev, 0x78, &pci_cmd); 589 pci_read_config_byte(dev, reg, &pci_cmd);
577 if ( !(pci_cmd & 1<<7) ) { 590 if ( !(pci_cmd & 1<<7) ) {
578 pci_cmd |= 1<<7; 591 pci_cmd |= 1<<7;
579 pci_write_config_byte(dev, 0x78, pci_cmd); 592 pci_write_config_byte(dev, reg, pci_cmd);
580 } 593 }
581 return 1; 594 return 1;
582 } 595 }
@@ -681,19 +694,29 @@ static int __init longhaul_cpu_init(struct cpufreq_policy *policy)
681 /* Check ACPI support for C3 state */ 694 /* Check ACPI support for C3 state */
682 cx = &pr->power.states[ACPI_STATE_C3]; 695 cx = &pr->power.states[ACPI_STATE_C3];
683 if (cx->address == 0 || 696 if (cx->address == 0 ||
684 (cx->latency > 1000 && ignore_latency == 0) ) 697 (cx->latency > 1000 && ignore_latency == 0) ) {
685 goto err_acpi; 698 if (enable_arbiter_disable()) {
699 port22_en = 1;
700 } else {
701 goto err_acpi;
702 }
703 }
686 704
687 } else { 705 } else {
688 /* Check ACPI support for bus master arbiter disable */ 706 /* Check ACPI support for bus master arbiter disable */
689 if (!pr->flags.bm_control) { 707 if (!pr->flags.bm_control) {
690 if (!enable_arbiter_disable()) { 708 if (enable_arbiter_disable()) {
691 printk(KERN_ERR PFX "No ACPI support. No VT8601 host bridge. Aborting.\n");
692 return -ENODEV;
693 } else
694 port22_en = 1; 709 port22_en = 1;
710 } else {
711 goto err_acpi;
712 }
695 } 713 }
696 } 714 }
715 if (!port22_en) {
716 printk (KERN_INFO PFX "Using ACPI support.\n");
717 } else {
718 printk (KERN_INFO PFX "Using northbridge support.\n");
719 }
697 720
698 ret = longhaul_get_ranges(); 721 ret = longhaul_get_ranges();
699 if (ret != 0) 722 if (ret != 0)
@@ -716,7 +739,7 @@ static int __init longhaul_cpu_init(struct cpufreq_policy *policy)
716 return 0; 739 return 0;
717 740
718err_acpi: 741err_acpi:
719 printk(KERN_ERR PFX "No ACPI support for CPU frequency changes.\n"); 742 printk(KERN_ERR PFX "No ACPI support. No VT8601 or VT8623 northbridge. Aborting.\n");
720 return -ENODEV; 743 return -ENODEV;
721} 744}
722 745