Supposedly Innocent Pointer Assignment causes trouble

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
Post Reply
srg

Supposedly Innocent Pointer Assignment causes trouble

Post by srg »

Hi

(Sorry about the last post but since then I've found out that it's nothing to do with the ISR, just the pointer assignment.

I'm trying to make a stack for recording physical pages that havn't been mapped into any any address spaces yet but I'm getting some very odd errors with a seemingly innocent pointer assignment.

Here's the code:

Code: Select all

/* ###################
; mem()
;
; Description:   Sets up the SG-OS memory manager, it first
;                   retreves the size of the machine's ram from the
;                   Multiboot returned information, and then starts
;                   building up the unallocated page stack.
;
; C Prototype: int mem(multiboot_info_t *boot_info);
;
; Parameters: boot_info - Pointer to the Multiboot returned
;                  information
;
; Returns: 0 = Success, 1 = couldn't get available memory, 2 =
; ...
*/
int mem()
{
   
   memory_map_t *mmap_ptr;
   unsigned int count;
   unsigned int *page_dir_ptr = (unsigned int*)
   KERNEL_PAGE_DIR_LOCATION;
   unsigned int next_unused_page;
   
/* 1. Get the amount of physical RAM installed in the
 * machine. Check bit 6 of the flags to see if the mem map 
 * is valid.
 * This is the profered method, but doesn't work on old
 * machines
 */
   if (boot_information->flags & 0x40)
   {
      /* It is, great, now to read the size/structure pairs */
      mmap_ptr = (memory_map_t *)boot_information->mmap_addr;
      /* Now to check each pair (ignoring the size and 
                 * using 24 bytes for each one). If the structure is
       * describing available memory, then add it's length
                 * to the total and then go to the next one!
       */
      for (count = 0; count < boot_information->mmap_length ;
          count += MMAP_PAIR_SIZE)
      {
         if (mmap_ptr->type == 1)
            mem_amount += mmap_ptr->length_low;
         mmap_ptr++;
      }
   }
   else
   {
      /* Otherwise check bit 0 to see if we can get an
                 * older style memory size reading.
       * This is the older, less reliable method.
       */
      if (boot_information->flags & 1)
         mem_amount = boot_information->mem_upper
                         + 1024;/*KB, add the first 1MB to total*/
      else
         /* Oh well, just fail then */
         return 1;

      /* Current value is in Kilobytes, I want it in bytes */
      mem_amount *= 1024;
   }

   /* 2. Setup the Unallocated page stack */
   unallocated_stack_ptr = KERNEL_PAGE_DIR_LOCATION + 0x2000;
   
   /* The current highest point of used memory is at the top
         * of the unallocated page stack, we need to find out the
         * next unused page
         */
   next_unused_page = unallocated_stack_ptr + (4 * (mem_amount /          PAGE_SIZE));
   next_unused_page = (next_unused_page & 0xFFFFF000) + 0x1000;
   

   /* Now add the addresses of the physical pages that
         * are'nt allocated
         */
   for (count = 0; count < (mem_amount / PAGE_SIZE) ; count++)
   {
      *unallocated_stack_ptr = next_unused_page;
      unallocated_stack_ptr++;
      next_unused_page += 0x1000;
   }
   
   return 0;
}


Anyway, when I make and assignment to the memory pointed to by this pointer, it could be any address, or anything being assigned to it, so this line:

*unallocated_stack_ptr = next_unused_page;

I just get this error from Bochs if I have interrupts dissabled:

[CPU ] fetch_raw_descriptor: LDTR.valid=0

Or, if i have interrupts enabled:

[CPU ] iret: AR byte indicated non code segment.

If I run this through VMWare, it just prints a pattern of characters on the screen,

The strangest thing is that on real hardware (AMD athlons at least) it works quite happily.

What am I doing wrong?
Thanks
srg
User avatar
Pype.Clicker
Member
Member
Posts: 5964
Joined: Wed Oct 18, 2006 2:31 am
Location: In a galaxy, far, far away
Contact:

Re:Supposedly Innocent Pointer Assignment causes trouble

Post by Pype.Clicker »

clearly, your interrupt handler is doing something nasty and i would make sure it correctly pops all the things it pushed before going later.

At the 'LDTR.valid=0', this occurs when you (by mistake) try to load a LDT-related selector in a segment register while no LDT has been set up. This usually means you're popping trash in a segment register.
srg

Re:Supposedly Innocent Pointer Assignment causes trouble

Post by srg »

D'oh, even simpler than that.

I forgot that I'm running at 3GB virtual addresses, so the pointer was pointing at 0x20xxxx when it should have been pointing at 0xC020xxxx. This meant that I was trying to write to memory that hasn't been mapped yet.

Changed that minor mistake and it works in Bochs and VMware perfectly. I just wonder why it worked before on an athlon.

anyway, thanks for the ideas
srg
User avatar
Candy
Member
Member
Posts: 3882
Joined: Tue Oct 17, 2006 11:33 pm
Location: Eindhoven

Re:Supposedly Innocent Pointer Assignment causes trouble

Post by Candy »

srg wrote: Changed that minor mistake and it works in Bochs and VMware perfectly. I just wonder why it worked before on an athlon.
Your physical athlon might have a larger TLB than Vmware/Bochs, so it'd not be swapped out. Not sure of course.
srg

Re:Supposedly Innocent Pointer Assignment causes trouble

Post by srg »

Candy wrote:
srg wrote: Changed that minor mistake and it works in Bochs and VMware perfectly. I just wonder why it worked before on an athlon.
Your physical athlon might have a larger TLB than Vmware/Bochs, so it'd not be swapped out. Not sure of course.
You might be right there, The standard Windows binary version of bochs is based on the Pentium. VMWare is based on a Pentium II.

srg
User avatar
Candy
Member
Member
Posts: 3882
Joined: Tue Oct 17, 2006 11:33 pm
Location: Eindhoven

Re:Supposedly Innocent Pointer Assignment causes trouble

Post by Candy »

srg wrote: You might be right there, The standard Windows binary version of bochs is based on the Pentium. VMWare is based on a Pentium II.
Virtual computers don't really need TLB's. Especially VMware, which probably shares it with windows.
Post Reply