SimpleOS

LXR

Navigation



Site hébergé par : enix

The LXR Cross Referencer for SOS

source navigation ]
diff markup ]
identifier search ]
general search ]
 
 
Article:1 ] [ 2 ] [ 3 ] [ 4 ] [ 5 ] [ 6 ] [ 6.5 ] [ 7 ] [ 7.5 ] [ 8 ] [ 9 ] [ 9.5 ]

Diff markup

Differences between /hwcore/idt.c (Article 4) and /hwcore/idt.c (Article 9)


001 /* Copyright (C) 2004  David Decotigny            001 /* Copyright (C) 2004  David Decotigny
002    Copyright (C) 1999  Free Software Foundatio << 
003                                                   002 
004    This program is free software; you can redi    003    This program is free software; you can redistribute it and/or
005    modify it under the terms of the GNU Genera    004    modify it under the terms of the GNU General Public License
006    as published by the Free Software Foundatio    005    as published by the Free Software Foundation; either version 2
007    of the License, or (at your option) any lat    006    of the License, or (at your option) any later version.
008                                                   007    
009    This program is distributed in the hope tha    008    This program is distributed in the hope that it will be useful,
010    but WITHOUT ANY WARRANTY; without even the     009    but WITHOUT ANY WARRANTY; without even the implied warranty of
011    MERCHANTABILITY or FITNESS FOR A PARTICULAR    010    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
012    GNU General Public License for more details    011    GNU General Public License for more details.
013                                                   012    
014    You should have received a copy of the GNU     013    You should have received a copy of the GNU General Public License
015    along with this program; if not, write to t    014    along with this program; if not, write to the Free Software
016    Foundation, Inc., 59 Temple Place - Suite 3    015    Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
017    USA.                                           016    USA. 
018 */                                                017 */
019 #include "segment.h"                              018 #include "segment.h"
020                                                   019 
021 #include "idt.h"                                  020 #include "idt.h"
022                                                   021 
023 /**                                               022 /**
024  * An entry in the IDT, or "IDTE" in the follo    023  * An entry in the IDT, or "IDTE" in the following, ie a reference to
025  * a interrupt/trap routine or a task gate to     024  * a interrupt/trap routine or a task gate to handle the sw/hw
026  * interrupts and exceptions.                     025  * interrupts and exceptions.
027  *                                                026  *
028  * @see figure 5-2, intel x86 doc, vol 3          027  * @see figure 5-2, intel x86 doc, vol 3
029  */                                               028  */
030 struct x86_idt_entry                              029 struct x86_idt_entry
031 {                                                 030 {
032   /* Low dword */                                 031   /* Low dword */
033   sos_ui16_t offset_low;  /* 15..0, offset of     032   sos_ui16_t offset_low;  /* 15..0, offset of the routine in the segment */
034   sos_ui16_t seg_sel;     /* 31..16, the ID of    033   sos_ui16_t seg_sel;     /* 31..16, the ID of the segment */
035                                                   034 
036   /* High dword */                                035   /* High dword */
037   sos_ui8_t reserved:5;   /* 4..0 */              036   sos_ui8_t reserved:5;   /* 4..0 */
038   sos_ui8_t flags:3;      /* 7..5 */              037   sos_ui8_t flags:3;      /* 7..5 */
039   sos_ui8_t type:3;       /* 10..8 (interrupt     038   sos_ui8_t type:3;       /* 10..8 (interrupt gate, trap gate...) */
040   sos_ui8_t op_size:1;    /* 11 (0=16bits inst    039   sos_ui8_t op_size:1;    /* 11 (0=16bits instructions, 1=32bits instr.) */
041   sos_ui8_t zero:1;       /* 12 */                040   sos_ui8_t zero:1;       /* 12 */
042   sos_ui8_t dpl:2;        /* 14..13 */            041   sos_ui8_t dpl:2;        /* 14..13 */
043   sos_ui8_t present:1;    /* 15 */                042   sos_ui8_t present:1;    /* 15 */
044   sos_ui16_t offset_high; /* 31..16 */            043   sos_ui16_t offset_high; /* 31..16 */
045 } __attribute__((packed));                        044 } __attribute__((packed));
046                                                   045 
047                                                   046 
048 /**                                               047 /**
049  * The IDT register, which stores the address     048  * The IDT register, which stores the address and size of the
050  * IDT.                                           049  * IDT.
051  *                                                050  *
052  * @see Intel x86 doc vol 3, section 2.4, figu    051  * @see Intel x86 doc vol 3, section 2.4, figure 2-4
053  */                                               052  */
054 struct x86_idt_register                           053 struct x86_idt_register
055 {                                                 054 {
056   /* The maximum GDT offset allowed to access     055   /* The maximum GDT offset allowed to access an entry in the GDT */
057   sos_ui16_t  limit;                              056   sos_ui16_t  limit;
058                                                   057 
059   /* This is not exactly a "virtual" address,     058   /* This is not exactly a "virtual" address, ie an adddress such as
060      those of instructions and data; this is a    059      those of instructions and data; this is a "linear" address, ie an
061      address in the paged memory. However, in     060      address in the paged memory. However, in SOS we configure the
062      segmented memory as a "flat" space: the 0    061      segmented memory as a "flat" space: the 0-4GB segment-based (ie
063      "virtual") addresses directly map to the     062      "virtual") addresses directly map to the 0-4GB paged memory (ie
064      "linear"), so that the "linear" addresses    063      "linear"), so that the "linear" addresses are numerically equal
065      to the "virtual" addresses: this base_add    064      to the "virtual" addresses: this base_addr will thus be the same
066      as the address of the gdt array */           065      as the address of the gdt array */
067   sos_ui32_t base_addr;                           066   sos_ui32_t base_addr;
068 } __attribute__((packed, aligned (8)));           067 } __attribute__((packed, aligned (8)));
069                                                   068 
070                                                   069 
071 static struct x86_idt_entry    idt[SOS_IDTE_NU    070 static struct x86_idt_entry    idt[SOS_IDTE_NUM];
072                                                   071 
073 sos_ret_t sos_idt_setup()                      !! 072 sos_ret_t sos_idt_subsystem_setup()
074 {                                                 073 {
075   struct x86_idt_register idtr;                   074   struct x86_idt_register idtr;
076   int i;                                          075   int i;
077                                                   076 
078   for (i = 0 ;                                    077   for (i = 0 ;
079        i < SOS_IDTE_NUM ;                         078        i < SOS_IDTE_NUM ;
080        i++)                                       079        i++)
081     {                                             080     {
082       struct x86_idt_entry *idte = idt + i;       081       struct x86_idt_entry *idte = idt + i;
083                                                   082 
084       /* Setup an empty IDTE interrupt gate, s    083       /* Setup an empty IDTE interrupt gate, see figure 5-2 in Intel
085          x86 doc, vol 3 */                        084          x86 doc, vol 3 */
086       idte->seg_sel   = SOS_BUILD_SEGMENT_REG_    085       idte->seg_sel   = SOS_BUILD_SEGMENT_REG_VALUE(0, FALSE, SOS_SEG_KCODE);
087       idte->reserved  = 0;                        086       idte->reserved  = 0;
088       idte->flags     = 0;                        087       idte->flags     = 0;
089       idte->type      = 0x6; /* Interrupt gate    088       idte->type      = 0x6; /* Interrupt gate (110b) */
090       idte->op_size   = 1;   /* 32bits instruc    089       idte->op_size   = 1;   /* 32bits instructions */
091       idte->zero      = 0;                        090       idte->zero      = 0;
092                                                   091 
093       /* Disable this IDT entry for the moment    092       /* Disable this IDT entry for the moment */
094       sos_idt_set_handler(i, (sos_vaddr_t)NULL    093       sos_idt_set_handler(i, (sos_vaddr_t)NULL, 0/* Don't care */);
095     }                                             094     }
096                                                   095 
097   /*                                              096   /*
098    * Setup the IDT register, see Intel x86 doc    097    * Setup the IDT register, see Intel x86 doc vol 3, section 5.8.
099    */                                             098    */
100                                                   099 
101   /* Address of the IDT */                        100   /* Address of the IDT */
102   idtr.base_addr  = (sos_ui32_t) idt;             101   idtr.base_addr  = (sos_ui32_t) idt;
103                                                   102 
104   /* The limit is the maximum offset in bytes     103   /* The limit is the maximum offset in bytes from the base address of
105      the IDT */                                   104      the IDT */
106   idtr.limit      = sizeof(idt) - 1;              105   idtr.limit      = sizeof(idt) - 1;
107                                                   106 
108   /* Commit the IDT into the CPU */               107   /* Commit the IDT into the CPU */
109   asm volatile ("lidt %0\n"::"m"(idtr):"memory    108   asm volatile ("lidt %0\n"::"m"(idtr):"memory");
110                                                   109   
111   return SOS_OK;                                  110   return SOS_OK;
112 }                                                 111 }
113                                                   112 
114                                                   113 
115 sos_ret_t sos_idt_set_handler(int index,          114 sos_ret_t sos_idt_set_handler(int index,
116                               sos_vaddr_t hand    115                               sos_vaddr_t handler_address,
117                               int lowest_privi    116                               int lowest_priviledge /* 0..3 */)
118 {                                                 117 {
119   struct x86_idt_entry *idte;                     118   struct x86_idt_entry *idte;
120                                                   119 
121   if ((index < 0) || (index >= SOS_IDTE_NUM))     120   if ((index < 0) || (index >= SOS_IDTE_NUM))
122     return -SOS_EINVAL;                           121     return -SOS_EINVAL;
123   if ((lowest_priviledge < 0) || (lowest_privi    122   if ((lowest_priviledge < 0) || (lowest_priviledge > 3))
124     return -SOS_EINVAL;                           123     return -SOS_EINVAL;
125                                                   124   
126   idte = idt + index;                             125   idte = idt + index;
127   if (handler_address != (sos_vaddr_t)NULL)       126   if (handler_address != (sos_vaddr_t)NULL)
128     {                                             127     {
129       idte->offset_low  = handler_address & 0x    128       idte->offset_low  = handler_address & 0xffff;
130       idte->offset_high = (handler_address >>     129       idte->offset_high = (handler_address >> 16) & 0xffff;
131       idte->dpl         = lowest_priviledge;      130       idte->dpl         = lowest_priviledge;
132       idte->present     = 1;   /* Yes, there i    131       idte->present     = 1;   /* Yes, there is a handler */
133     }                                             132     }
134   else /* Disable this IDT entry */               133   else /* Disable this IDT entry */
135     {                                             134     {
136       idte->offset_low  = 0;                      135       idte->offset_low  = 0;
137       idte->offset_high = 0;                      136       idte->offset_high = 0;
138       idte->dpl         = 0;                      137       idte->dpl         = 0;
139       idte->present     = 0;   /* No, there is    138       idte->present     = 0;   /* No, there is no handler */
140     }                                             139     }
141                                                   140 
142   return SOS_OK;                                  141   return SOS_OK;
143 }                                                 142 }
144                                                   143 
145                                                   144 
146 sos_ret_t sos_idt_get_handler(int index,          145 sos_ret_t sos_idt_get_handler(int index,
147                               sos_vaddr_t *han    146                               sos_vaddr_t *handler_address,
148                               int *lowest_priv    147                               int *lowest_priviledge)
149 {                                                 148 {
150   if ((index < 0) || (index >= SOS_IDTE_NUM))     149   if ((index < 0) || (index >= SOS_IDTE_NUM))
151     return -SOS_EINVAL;                           150     return -SOS_EINVAL;
152                                                   151 
153   if (handler_address != NULL)                    152   if (handler_address != NULL)
154     *handler_address = idt[index].offset_low      153     *handler_address = idt[index].offset_low
155                        | (idt[index].offset_hi    154                        | (idt[index].offset_high << 16);
156   if (lowest_priviledge != NULL)                  155   if (lowest_priviledge != NULL)
157     *lowest_priviledge = idt[index].dpl;          156     *lowest_priviledge = idt[index].dpl;
158                                                   157 
159   return SOS_OK;                                  158   return SOS_OK;
160 }                                                 159 }
                                                      

source navigation ] diff markup ] identifier search ] general search ]