OSDev

для всех
Текущее время: 14 дек 2024, 07:02

Часовой пояс: UTC + 3 часа




Начать новую тему Ответить на тему  [ 1 сообщение ] 
Автор Сообщение
СообщениеДобавлено: 28 мар 2013, 21:03 

Зарегистрирован: 23 ноя 2012, 13:02
Сообщения: 27
Здравствуйте, тут недавно заметил, что у меня после завершения процесса возникает утечка памяти в 8 кб. Начал разбираться в чем прикол, обнаружилось, что просто я забывал удалять директорий страниц, который был создан под процесс.
Вот так вот у меня устроены директории страниц:
Код:
typedef struct page_table
{
   page_t pages[1024];
} page_table_t;

typedef struct page_directory
{
   page_table_t *tables[1024];
   uint32 tablesPhysical [1024];
   uint32 physicalAddr;
} page_directory_t;

Соответсвенно для удаления директория написал такую функцию:
Код:
void destroy_directory (page_directory_t *src)
{
   int i;
   for (i = 0; i < 1024; i++)
   {
      if (!src->tables[i])
         continue;
      if (src->tables[i] != kernel_directory->tables[i])
         kfree(src->tables[i]);
   }
   kfree (src);
}

Вот, вроде бы утечка памяти убралась, то есть после создания и умирания процессов вся память освобождается. НО!! При таком подходе система работает только в том случае, когда: создается процесс, убивается... Все работает! Но система перезагружается, если создам 2 процесса (для примера): создаю первый который запускается и умирает, после этого создаю процесс, который загружается и работает (не умирает!!!), делаю попытку создать второй такой процесс - система умирает.
Вот функции для копирования директории страниц:
Код:
static page_table_t *clone_table(page_table_t *src, uint32 *physAddr)
{
   page_table_t *table = (page_table_t*)kmalloc_ap(sizeof(page_table_t), physAddr);
   memset((uint8*)table, 0, sizeof(page_table_t));

   int i;
   for (i = 0; i < 1024; i++)
   {
      if (!src->pages[i].frame)
         continue;
      alloc_frame(&table->pages[i], 0, 0);
      if (src->pages[i].present) table->pages[i].present = 1;
      if (src->pages[i].rw)      table->pages[i].rw = 1;
      if (src->pages[i].user)    table->pages[i].user = 1;
      if (src->pages[i].accessed)table->pages[i].accessed = 1;
      if (src->pages[i].dirty)   table->pages[i].dirty = 1;
      copy_page_physical(src->pages[i].frame*PAGE_SIZE, table->pages[i].frame*PAGE_SIZE);
   }
   return table;
}

page_directory_t *clone_directory(page_directory_t *src)
{
   uint32 phys;
   page_directory_t *dir = (page_directory_t*)kmalloc_ap(sizeof(page_directory_t), &phys);
   memset((uint8*)dir, 0, sizeof(page_directory_t));

   uint32 offset = (uint32)dir->tablesPhysical - (uint32)dir;
   dir->physicalAddr = phys + offset;

   int i;
   for (i = 0; i < 1024; i++)
   {
      if (!src->tables[i])
         continue;
      if (kernel_directory->tables[i] == src->tables[i])
      {
         dir->tables[i] = src->tables[i];
         dir->tablesPhysical[i] = src->tablesPhysical[i];
      }
      else
      {
         uint32 phys;
         dir->tables[i] = clone_table(src->tables[i], &phys);
         dir->tablesPhysical[i] = phys | 0x07;
      }
   }
   return dir;
}

Поотлаживав я выяснил, что происходит ошибка в создании последнего запускаемого процесса при попытке копирования таблицы страниц... Все идет нормально, все правильно заполняется, но после вызова функции clone_table вся директория заполняется какими-то непонятными данными.
Не могу никак понять в чем тут может быть косяк...
Вот еще приведу функцию copy_page_physical:
Код:
copy_page_physical:
   push ebx
   pushf
   cli
   mov ebx, [esp+12]
   mov ecx, [esp+16]
 
   mov edx, cr0
   and edx, 0x7fffffff
   mov cr0, edx
 
   mov edx, 1024
 
.loop:
   mov eax, [ebx]
   mov [ecx], eax
   add ebx, 4   
   add ecx, 4
   dec edx
   jnz .loop             
 
   mov edx, cr0
   or  edx, 0x80000000
   mov cr0, edx
 
   popf
   pop ebx
    ret


Вернуться к началу
 Профиль  
 
Показать сообщения за:  Поле сортировки  
Начать новую тему Ответить на тему  [ 1 сообщение ] 

Часовой пояс: UTC + 3 часа


Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 1


Вы не можете начинать темы
Вы не можете отвечать на сообщения
Вы не можете редактировать свои сообщения
Вы не можете удалять свои сообщения
Вы не можете добавлять вложения

Найти:
Перейти:  
cron
Создано на основе phpBB® Forum Software © phpBB Group
Русская поддержка phpBB