linux/arch/i386/kernel/bootflag.c
<<
>>
Prefs
   1/*
   2 *      Implement 'Simple Boot Flag Specification 2.0'
   3 */
   4
   5
   6#include <linux/types.h>
   7#include <linux/kernel.h>
   8#include <linux/init.h>
   9#include <linux/string.h>
  10#include <linux/slab.h>
  11#include <linux/spinlock.h>
  12#include <linux/acpi.h>
  13#include <asm/io.h>
  14
  15#include <linux/mc146818rtc.h>
  16
  17
  18#define SBF_RESERVED (0x78)
  19#define SBF_PNPOS    (1<<0)
  20#define SBF_BOOTING  (1<<1)
  21#define SBF_DIAG     (1<<2)
  22#define SBF_PARITY   (1<<7)
  23
  24
  25int sbf_port __initdata = -1;   /* set via acpi_boot_init() */
  26
  27
  28static int __init parity(u8 v)
  29{
  30        int x = 0;
  31        int i;
  32        
  33        for(i=0;i<8;i++)
  34        {
  35                x^=(v&1);
  36                v>>=1;
  37        }
  38        return x;
  39}
  40
  41static void __init sbf_write(u8 v)
  42{
  43        unsigned long flags;
  44        if(sbf_port != -1)
  45        {
  46                v &= ~SBF_PARITY;
  47                if(!parity(v))
  48                        v|=SBF_PARITY;
  49
  50                printk(KERN_INFO "Simple Boot Flag at 0x%x set to 0x%x\n", sbf_port, v);
  51
  52                spin_lock_irqsave(&rtc_lock, flags);
  53                CMOS_WRITE(v, sbf_port);
  54                spin_unlock_irqrestore(&rtc_lock, flags);
  55        }
  56}
  57
  58static u8 __init sbf_read(void)
  59{
  60        u8 v;
  61        unsigned long flags;
  62        if(sbf_port == -1)
  63                return 0;
  64        spin_lock_irqsave(&rtc_lock, flags);
  65        v = CMOS_READ(sbf_port);
  66        spin_unlock_irqrestore(&rtc_lock, flags);
  67        return v;
  68}
  69
  70static int __init sbf_value_valid(u8 v)
  71{
  72        if(v&SBF_RESERVED)              /* Reserved bits */
  73                return 0;
  74        if(!parity(v))
  75                return 0;
  76        return 1;
  77}
  78
  79static int __init sbf_init(void)
  80{
  81        u8 v;
  82        if(sbf_port == -1)
  83                return 0;
  84        v = sbf_read();
  85        if(!sbf_value_valid(v))
  86                printk(KERN_WARNING "Simple Boot Flag value 0x%x read from CMOS RAM was invalid\n",v);
  87
  88        v &= ~SBF_RESERVED;
  89        v &= ~SBF_BOOTING;
  90        v &= ~SBF_DIAG;
  91#if defined(CONFIG_ISAPNP)
  92        v |= SBF_PNPOS;
  93#endif
  94        sbf_write(v);
  95        return 0;
  96}
  97
  98module_init(sbf_init);
  99
lxr.linux.no kindly hosted by Redpill Linpro AS, provider of Linux consulting and operations services since 1995.