Changeset 50a4e25 in mainline


Ignore:
Timestamp:
2005-09-06T21:30:55Z (19 years ago)
Author:
Sergey Bondari <bondari@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
2cd073bd
Parents:
b49f4ae
Message:

Fixed possible non-consequentive local apic madt entries
Request for peer review - was not possible to test.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • arch/ia32/src/acpi/madt.c

    rb49f4ae r50a4e25  
    3737#include <config.h>
    3838#include <print.h>
     39#include <mm/heap.h>
     40#include <memstr.h>
    3941
    4042struct acpi_madt *acpi_madt = NULL;
     
    4244#ifdef __SMP__
    4345
    44 /*
    45  * NOTE: it is currently not completely clear to the authors of SPARTAN whether
    46  * MADT can exist in such a form that entries of the same type are not consecutive.
    47  * Because of this uncertainity, some entry types are explicitly checked for
    48  * being consecutive with other entries of the same kind.
    49  */
    50 
    51 static void madt_l_apic_entry(struct madt_l_apic *la, __u8 prev_type);
    52 static void madt_io_apic_entry(struct madt_io_apic *ioa, __u8 prev_type);
     46static void madt_l_apic_entry(struct madt_l_apic *la, __u32 index);
     47static void madt_io_apic_entry(struct madt_io_apic *ioa, __u32 index);
    5348
    5449struct madt_l_apic *madt_l_apic_entries = NULL;
    5550struct madt_io_apic *madt_io_apic_entries = NULL;
    5651
     52__u32 madt_l_apic_entry_index = 0;
     53__u32 madt_io_apic_entry_index = 0;
    5754int madt_l_apic_entry_cnt = 0;
    5855int madt_io_apic_entry_cnt = 0;
     56
     57struct madt_apic_header * * madt_entries_index = NULL;
     58int madt_entries_index_cnt = 0;
    5959
    6060char *entry[] = {
     
    9393{
    9494        ASSERT(i < madt_l_apic_entry_cnt);
    95         return madt_l_apic_entries[i].flags & 0x1;
     95        return ((struct madt_l_apic *) madt_entries_index[madt_l_apic_entry_index + i])->flags & 0x1;
     96
    9697}
    9798
     
    99100{
    100101        ASSERT(i < madt_l_apic_entry_cnt);
    101         return madt_l_apic_entries[i].apic_id == l_apic_id();
     102        return ((struct madt_l_apic *) madt_entries_index[madt_l_apic_entry_index + i])->apic_id == l_apic_id();
    102103}
    103104
     
    105106{
    106107        ASSERT(i < madt_l_apic_entry_cnt);
    107         return madt_l_apic_entries[i].apic_id;
     108        return ((struct madt_l_apic *) madt_entries_index[madt_l_apic_entry_index + i])->apic_id;
    108109}
    109110
     
    111112{
    112113        struct madt_apic_header *end = (struct madt_apic_header *) (((__u8 *) acpi_madt) + acpi_madt->header.length);
    113         struct madt_apic_header *h = &acpi_madt->apic_header[0];
    114         __u8 prev_type = 0; /* used to detect inconsecutive entries */
    115 
    116 
    117         l_apic = (__u32 *) (__native) acpi_madt->l_apic_address;
    118 
    119         while (h < end) {
     114        struct madt_apic_header *h;
     115
     116        /* calculate madt entries */
     117        for (h = &acpi_madt->apic_header[0]; h < end; h = (struct madt_apic_header *) (((__u8 *) h) + h->length)) {
     118                madt_entries_index_cnt++;
     119        }
     120        printf("MADT: Found %d entries\n", madt_entries_index_cnt);
     121
     122        /* create madt apic entries index array */
     123        madt_entries_index = (struct madt_apic_header * *) malloc(madt_entries_index_cnt * sizeof(struct madt_apic_header * *));
     124
     125        __u32 index = 0;
     126
     127        for (h = &acpi_madt->apic_header[0]; h < end; h = (struct madt_apic_header *) (((__u8 *) h) + h->length)) {
     128                madt_entries_index[index++] = h;
     129        }
     130
     131
     132        /* Bublesort madt index. Quicksort later. */
     133        bool done = false;
     134
     135        while (!done) {
     136                done = true;
     137                for (index = 0; index < madt_entries_index_cnt - 1; index++) {
     138                        if (madt_entries_index[index]->type > madt_entries_index[index + 1]->type) {
     139                                h = madt_entries_index[index];
     140                                madt_entries_index[index] = madt_entries_index[index + 1];
     141                                madt_entries_index[index + 1] = h;
     142                                done = false;
     143                        }
     144                }
     145       
     146        }
     147               
     148
     149        /* Parse MADT entries */       
     150        for (index = 0; index < madt_entries_index_cnt - 1; index++) {
     151                h = madt_entries_index[index];
    120152                switch (h->type) {
    121153                        case MADT_L_APIC:
    122                                 madt_l_apic_entry((struct madt_l_apic *) h, prev_type);
     154                                madt_l_apic_entry((struct madt_l_apic *) h, index);
    123155                                break;
    124156                        case MADT_IO_APIC:
    125                                 madt_io_apic_entry((struct madt_io_apic *) h, prev_type);
     157                                madt_io_apic_entry((struct madt_io_apic *) h, index);
    126158                                break;
    127159                        case MADT_INTR_SRC_OVRD:
     
    144176                                break;
    145177                }
    146                 prev_type = h->type;
    147                 h = (struct madt_apic_header *) (((__u8 *) h) + h->length);
    148         }
     178       
     179       
     180        }
     181       
    149182
    150183        if (madt_l_apic_entry_cnt)
     
    152185}
    153186 
    154 void madt_l_apic_entry(struct madt_l_apic *la, __u8 prev_type)
    155 {
    156         /* check for consecutiveness */
    157         if (madt_l_apic_entry_cnt && prev_type != MADT_L_APIC)
    158         panic("%s entries are not consecuitve\n", entry[MADT_L_APIC]);
    159 
    160         if (!madt_l_apic_entry_cnt++)
    161                 madt_l_apic_entries = la;
     187
     188void madt_l_apic_entry(struct madt_l_apic *la, __u32 index)
     189{
     190        if (!madt_l_apic_entry_cnt++) {
     191                madt_l_apic_entry_index = index;
     192        }
    162193               
    163194        if (!(la->flags & 0x1)) {
     
    169200}
    170201
    171 void madt_io_apic_entry(struct madt_io_apic *ioa, __u8 prev_type)
    172 {
    173         /* check for consecutiveness */
    174         if (madt_io_apic_entry_cnt && prev_type != MADT_IO_APIC)
    175         panic("%s entries are not consecuitve\n", entry[MADT_IO_APIC]);
    176 
     202void madt_io_apic_entry(struct madt_io_apic *ioa, __u32 index)
     203{
    177204        if (!madt_io_apic_entry_cnt++) {
    178                 madt_io_apic_entries = ioa;
     205                /* remember index of the first io apic entry */
     206                madt_io_apic_entry_index = index;
     207                /* ????!!!! */
    179208                io_apic = (__u32 *) (__native) ioa->io_apic_address;
    180         }
    181         else {
     209        } else {
    182210                /* currently not supported */
    183211                return;
Note: See TracChangeset for help on using the changeset viewer.