⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 memory.cpp

📁 Jazmyn is a 32-bit, protected mode, multitasking OS which runs on i386 & above CPU`s. Its complete
💻 CPP
字号:
/*
 * Copyright (C) 2004, Thejesh AP. All rights reserved.
 */

#include <sys\types.h>
#include <jazmyn\const.h>
#include <null.h>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <dirent.h>
#include <mm\new.h>
#include <jazmyn\i386.h>
#include <jazmyn\desc.h>
#include <jazmyn\gdt.h>
#include <fs\devmgr.h>
#include <fs\fatvol.h>
#include <semaphore.h>
#include <fs\fatdriver.h>
#include <mm\heap.h>
#include <mm\paging.h>
#include <mm\memory.h>
#include <drivers\console.h>
#include <drivers\keyboard.h>

#define	_cs_sel		(0|7)
#define _ds_sel         (8|7)

extern paging           _paging_obj;
extern GDT              _gdt;
extern FATdriver        _FAT_driver;
extern char *environ[];

memory::memory()
{
	physical_base = NULL;
        _tss_sel = _gdt.set_tss((uint)&tss,sizeof(tss));
        _ldt_sel = _gdt.set_ldt((uint)&ldt[0],sizeof(ldt[0])*2);
}

memory::~memory()
{
	delete mm.virtual_page;
	delete mm.physical_page;
        _paging_obj.free_pages(physical_base);
	physical_base = NULL;
}


void memory::init_memory(void *buf,uint cs,uint ds,uint bss,uint ss,uint ep)
{
	CS = cs;
	DS = ds;
	BSS = bss;
	int db = DS + BSS;
	int n = db / PAGE_SIZE;
	if(db % PAGE_SIZE) n++;
	HEAP = (n*PAGE_SIZE - (DS + BSS)) + PAGE_SIZE;
	SS = ss;
	int total = CS + DS + BSS + HEAP + SS;

        entry_point = ep;

	mm.prog_pages = total / PAGE_SIZE;
	if(total % PAGE_SIZE) mm.prog_pages++;

	mm.virtual_page = new uint[mm.prog_pages];
	mm.physical_page = new uint[mm.prog_pages];
        if(!mm.virtual_page || !mm.physical_page)
        {
                cout<<"error allocting mem\n";
        }

      physical_base = _paging_obj.alloc_pages(mm.prog_pages);

	memcpy(physical_base,buf,mm.prog_pages*PAGE_SIZE);


	set_cs(ldt[0]);
	set_ds(ldt[1]);


      set_mem_map();
      set_table_entries();


//      _heap.init_heap(__VIRTUAL_BASE+CS+DS+BSS,HEAP);

      _heap.init_heap((uint)physical_base+CS+DS+BSS,HEAP);

	uint stk_top = mm.prog_pages * PAGE_SIZE - 1;
	set_tss(0,0,0,0,0,0,0,_ds_sel,_ds_sel,_ds_sel,_ds_sel,
		entry_point,_cs_sel,0x202,stk_top,_ds_sel);
}


void memory::set_cs(seg_desc &desc)
{
	uint limit = mm.prog_pages * PAGE_SIZE;
	desc.lim_low = limit&0xFFFF;
        desc.lim_flags = ((limit>>16)&0xF);
        desc.lim_flags = desc.lim_flags | D_BIG;


/*        desc.base_low  = __VIRTUAL_BASE&0xFFFF;
        desc.base_mid = (__VIRTUAL_BASE>>16)&0xFF;
        desc.base_high = (__VIRTUAL_BASE>>24)&0xFF;*/

        desc.base_low  = (uint)physical_base&0xFFFF;
        desc.base_mid = ((uint)physical_base>>16)&0xFF;
        desc.base_high = ((uint)physical_base>>24)&0xFF;


        desc.access = D_PRESENT|D_DPL_3|D_DT_APP|D_CODE|D_READ|D_CONFIRMING;
}

void memory::set_ds(seg_desc &desc)
{
	uint limit = mm.prog_pages * PAGE_SIZE;
	desc.lim_low = limit&0xFFFF;
        desc.lim_flags = ((limit>>16)&0xF);
        desc.lim_flags = desc.lim_flags|D_BIG;

/*        desc.base_low  = __VIRTUAL_BASE&0xFFFF;
        desc.base_mid = (__VIRTUAL_BASE>>16)&0xFF;
        desc.base_high = (__VIRTUAL_BASE>>24)&0xFF;*/


        desc.base_low  = (uint)physical_base&0xFFFF;
        desc.base_mid = ((uint)physical_base>>16)&0xFF;
        desc.base_high = ((uint)physical_base>>24)&0xFF;

        desc.access = D_PRESENT|D_DPL_3|D_DT_APP|D_DATA|D_WRITE;
}


void memory::set_mem_map()
{
	int virtual_page = __VIRTUAL_BASE / PAGE_SIZE;
        int physical_page = (uint)physical_base / PAGE_SIZE;

	for(int i=0;i<mm.prog_pages;i++)
	{
                mm.virtual_page[i] = virtual_page;
                mm.physical_page[i] = physical_page;

                virtual_page++;
                physical_page++;
	}
}

void memory::set_table_entries()
{
	for(int i=0;i<mm.prog_pages;i++)
	{
                int ptn = GET_TAB_NO(mm.virtual_page[i]);
                int pen = GET_ENT_NO(mm.virtual_page[i]);
		uint entry = (mm.physical_page[i]*PAGE_SIZE)|PRESENT|RD_WR|USR_SUP;
                _paging_obj.set_pte(ptn,pen,entry);
	}
}


void memory::set_tss(uint eax,uint ebx,uint ecx,uint edx,uint esi,uint edi,uint ebp,uint gs,
			uint fs,uint es,uint ds,uint eip,uint cs,uint eflags,uint esp,uint ss)
{

        tss.esp0 = (ulong)&kernel_stack[8191];
        tss.ss0 = KERNEL_SS_SEL;
	tss.cr3 = _CR3;
        tss.eip = eip;
        tss.eflag = eflags;
	tss.esp = esp;
        tss.ebp = ebp;
	tss.edi = edi;
	tss.esi = esi;
	tss.edx = edx;
	tss.ecx = ecx;
	tss.ebx = ebx;
	tss.eax = eax;
	tss.cs = cs;
	tss.ds = ds;
	tss.ss = ss;
	tss.es = es;
	tss.fs = fs;
	tss.gs = gs;
	tss.ldt = _ldt_sel;
	tss.trap = 0;
	tss.io_map_base = 0xFFFF;
	tss.end = 0xFF000000;
}



memory& memory::operator=(memory &parent)
{

	mm.prog_pages = parent.mm.prog_pages;
	mm.virtual_page = new uint[mm.prog_pages];
	mm.physical_page = new uint[mm.prog_pages];
        physical_base = _paging_obj.alloc_pages(mm.prog_pages);

        if(!mm.virtual_page || !mm.physical_page)
        {
                cout<<"Error allocating mem\n";
                getch();
        }

	set_mem_map();
	set_cs(ldt[0]);
	set_ds(ldt[1]);
	CS = parent.CS;
	DS = parent.DS;
	BSS = parent.BSS;
	HEAP = parent.HEAP;
	SS = parent.SS;
	memcpy(physical_base,parent.physical_base,mm.prog_pages*PAGE_SIZE);
	_heap = parent._heap;
	return *this;
}


int memory::try_to_replace(int fd,int argc,char **argv,char **env,uint cs,uint ds,uint bss,
				uint ss,uint ep)
{

        char **targv = (char**)NULL;
        if(argc)
        {
                targv = new char*[argc];
                for(int k=0;k<argc;k++)
                {
                        targv[k] = new char[strlen(argv[k])+1];
                        strcpy(targv[k],argv[k]);
                }
        }

	CS = cs;
	DS = ds;
	BSS = bss;
	int db = DS + BSS;
	int n = db / PAGE_SIZE;
	if(db % PAGE_SIZE) n++;
	HEAP = (n*PAGE_SIZE - (DS+BSS)) + PAGE_SIZE;
	SS = ss;
	int t = CS + DS + BSS + HEAP + SS;
        int total = mm.prog_pages * PAGE_SIZE;
	entry_point = ep;
	int sz = _FAT_driver.lseek(fd,0,SEEK_END);
	_FAT_driver.lseek(fd,0,SEEK_SET);
	if(t <= total)
	{
                // the new mem of process fits in old area
	}
	else
	{
                total = t;
	
		delete mm.virtual_page;
		delete mm.physical_page;
                _paging_obj.free_pages(physical_base);
		physical_base = NULL;
		
		mm.prog_pages = total / PAGE_SIZE;
		if(total % PAGE_SIZE) mm.prog_pages++;
                mm.virtual_page = new uint[mm.prog_pages];
                mm.physical_page = new uint[mm.prog_pages];
                physical_base = _paging_obj.alloc_pages(mm.prog_pages);
		set_cs(ldt[0]);
		set_ds(ldt[1]);		
		set_mem_map();
                set_table_entries();
	}

//        if(_FAT_driver.read(fd,(void*)__VIRTUAL_BASE,sz) != sz) return -1;
//        _heap.init_heap(__VIRTUAL_BASE+CS+DS+BSS,HEAP);


        if(_FAT_driver.read(fd,physical_base,sz) != sz) return -1;
        _heap.init_heap((uint)physical_base+CS+DS+BSS,HEAP);

	
	char **mmargv;
	mmargv = (char**)_heap.malloc(argc*sizeof(char*));
	for(int i=0;i<argc;i++)
	{
                mmargv[i] = (char*)_heap.malloc(strlen(argv[i])+1);
                strcpy(mmargv[i],targv[i]);
//                mmargv[i] = (char*)((uint)mmargv[i] - __VIRTUAL_BASE);
                mmargv[i] = (char*)((uint)mmargv[i] - (uint)physical_base);
	}

        int envcnt = 0;
        char **tmp = environ;
        while(*tmp)
        {
                envcnt++;
                tmp++;
        }

	char **mmenv;
        mmenv = (char**)_heap.malloc(envcnt*sizeof(char*));
        for(int i=0;i<envcnt;i++)
	{
                mmenv[i] = (char*)_heap.malloc(strlen(environ[i])+1);
                strcpy(mmenv[i],environ[i]);
//                mmenv[i] = (char*)((uint)mmenv[i] - __VIRTUAL_BASE);
                mmenv[i] = (char*)((uint)mmenv[i] - (uint)physical_base);
	}
        

	uint stk_top = mm.prog_pages * PAGE_SIZE - 1;

/*        set_tss(0,argc,((uint)mmargv - __VIRTUAL_BASE),((uint)mmenv - __VIRTUAL_BASE),
                0,0,0,_ds_sel,_ds_sel,_ds_sel,_ds_sel,entry_point,_cs_sel,0x202,
                stk_top,_ds_sel);*/


        set_tss(0,argc,mmargv ? ((uint)mmargv - (uint)physical_base) : 0,
                       mmenv ? ((uint)mmenv - (uint)physical_base) : 0,
                       0,0,0,_ds_sel,_ds_sel,_ds_sel,_ds_sel,
                       entry_point,_cs_sel,0x202,stk_top,_ds_sel);


        for(int m=0;m<argc;m++)
        delete targv[m];
        delete targv;
	return 0;
}


void memory::clear()
{
	delete mm.virtual_page;
	delete mm.physical_page;
        _paging_obj.free_pages(physical_base);
	physical_base = NULL;
}

void memory::show_tss()
{
        cout<<"tss selector :"<<_tss_sel<<endl;
        cout<<"esp0         :"<<tss.esp0<<endl;
        cout<<"ss0          :"<<tss.ss0<<endl;
        cout<<"cr3          :"<<tss.cr3<<endl;
        cout<<"eip          :"<<tss.eip<<endl;
        cout<<"eflags       :"<<tss.eflag<<endl;
        cout<<"esp          :"<<tss.esp<<endl;
        cout<<"ebp          :"<<tss.ebp<<endl;
        cout<<"edi          :"<<tss.edi<<endl;
        cout<<"esi          :"<<tss.esi<<endl;
        cout<<"edx          :"<<tss.edx<<endl;
        cout<<"ecx          :"<<tss.ecx<<endl;
        cout<<"ebx          :"<<tss.ebx<<endl;
        cout<<"eax          :"<<tss.eax<<endl;
        cout<<"cs           :"<<tss.cs<<endl;
        cout<<"ds           :"<<tss.ds<<endl;
        cout<<"ss           :"<<tss.ss<<endl;
        cout<<"es           :"<<tss.es<<endl; 
        cout<<"fs           :"<<tss.fs<<endl;
        cout<<"gs           :"<<tss.gs<<endl;
        cout<<"ldt          :"<<tss.ldt<<endl;
}      

void memory::show_ldt()
{
        seg_desc *d = &ldt[0];
        uint _b = (d->base_high<<24 | d->base_mid<<16 | d->base_low);
        cout<<"cs base :"<<_b<<endl;
        cout<<"cs limit:"<<d->lim_low<<endl;
        cout<<"cs access:"<<d->access<<endl;

        d = &ldt[1];
        _b = (d->base_high<<24 | d->base_mid<<16 | d->base_low);
        cout<<"ds base :"<<_b<<endl;
        cout<<"ds limit:"<<d->lim_low<<endl;
        cout<<"ds access:"<<d->access<<endl;
}        

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -