source: trunk/kernel/mm/vseg.c @ 654

Last change on this file since 654 was 651, checked in by alain, 5 years ago

1) Improve the VMM MMAP allocator: implement the "buddy" algorithm
to allocate only aligned blocks.
2) fix a bug in the pthread_join() / pthread_exit() mmechanism.

File size: 5.9 KB
RevLine 
[1]1/*
2 * vseg.c - virtual segment (vseg) related operations
3 *
[635]4 * Authors   Alain Greiner (2016,2017,2018,2019)
[1]5 *
6 * Copyright (c) UPMC Sorbonne Universites
7 *
8 * This file is part of ALMOS-MKH.
9 *
[184]10 * ALMOS-MKH is free software; you can redistribute it and/or modify it
[1]11 * under the terms of the GNU General Public License as published by
12 * the Free Software Foundation; version 2.0 of the License.
13 *
[184]14 * ALMOS-MKH is distributed in the hope that it will be useful, but
[1]15 * WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
17 * General Public License for more details.
18 *
19 * You should have received a copy of the GNU General Public License
[184]20 * along with ALMOS-MKH; if not, write to the Free Software Foundation,
[1]21 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
22 */
23
[457]24#include <hal_kernel_types.h>
[1]25#include <hal_special.h>
26#include <hal_remote.h>
27#include <list.h>
28#include <errno.h>
29#include <printk.h>
30#include <bits.h>
31#include <thread.h>
32#include <process.h>
33#include <ppm.h>
34#include <mapper.h>
35#include <vfs.h>
36#include <page.h>
37#include <vmm.h>
38#include <kmem.h>
39#include <vseg.h>
40
41////////////////////////////////////////////////////////////////////////////////////////
[18]42//   global variables for display / must be consistent with enum in "vseg.h"
[1]43////////////////////////////////////////////////////////////////////////////////////////
44
[101]45
46//////////////////////////////////////////
[184]47char * vseg_type_str( uint32_t vseg_type )
[1]48{
[101]49        if     ( vseg_type == VSEG_TYPE_CODE   ) return "CODE";
50        else if( vseg_type == VSEG_TYPE_DATA   ) return "DATA";
[407]51        else if( vseg_type == VSEG_TYPE_STACK  ) return "STAK";
[101]52        else if( vseg_type == VSEG_TYPE_ANON   ) return "ANON";
53        else if( vseg_type == VSEG_TYPE_FILE   ) return "FILE";
[407]54        else if( vseg_type == VSEG_TYPE_REMOTE ) return "REMO";
[623]55        else if( vseg_type == VSEG_TYPE_KCODE  ) return "KCOD";
56        else if( vseg_type == VSEG_TYPE_KDATA  ) return "KDAT";
57        else if( vseg_type == VSEG_TYPE_KDEV   ) return "KDEV";
[101]58    else                                     return "undefined";
59}
[1]60
[625]61///////////////////////////
[503]62vseg_t * vseg_alloc( void )
[1]63{
64    kmem_req_t   req;
65
[635]66    req.type  = KMEM_KCM;
67        req.order = bits_log2( sizeof(vseg_t) );
68        req.flags = AF_KERNEL | AF_ZERO;
[1]69
[635]70    return kmem_alloc( &req );
[1]71}
72
73///////////////////////////////
74void vseg_free( vseg_t * vseg )
75{
76    kmem_req_t  req;
77
[635]78        req.type = KMEM_KCM;
[1]79        req.ptr  = vseg;
80        kmem_free( &req );
81}
82
[651]83/////////////////////////////////////////
84void vseg_init_flags( vseg_t      * vseg,
85                      vseg_type_t   type )
[1]86{
87    // set vseg flags depending on type
[651]88        if( type == VSEG_TYPE_CODE )
[1]89    {
90        vseg->flags = VSEG_USER    |
[18]91                      VSEG_EXEC    |
[1]92                      VSEG_CACHE   |
93                      VSEG_PRIVATE ;
94    }
95    else if( type == VSEG_TYPE_STACK )
96    {
97        vseg->flags = VSEG_USER    |
98                      VSEG_WRITE   |
99                      VSEG_CACHE   |
[18]100                      VSEG_PRIVATE ;
[1]101    }
[18]102    else if( type == VSEG_TYPE_DATA )
[1]103    {
104        vseg->flags = VSEG_USER    |
105                      VSEG_WRITE   |
[18]106                      VSEG_CACHE   |
[1]107                      VSEG_DISTRIB ;
108    }
[18]109    else if( type == VSEG_TYPE_REMOTE )
[1]110    {
111        vseg->flags = VSEG_USER    |
[18]112                      VSEG_WRITE   |
113                      VSEG_CACHE   ;
[1]114    }
[18]115    else if( type == VSEG_TYPE_ANON )
[1]116    {
117        vseg->flags = VSEG_USER    |
118                      VSEG_WRITE   |
[407]119                      VSEG_CACHE; 
[1]120    }
[18]121    else if( type == VSEG_TYPE_FILE )
[1]122    {
123        vseg->flags = VSEG_USER    |
124                      VSEG_WRITE   |
125                      VSEG_CACHE   ;
126    }
[623]127    else if( type == VSEG_TYPE_KCODE )
128    {
129        vseg->flags = VSEG_EXEC    |
130                      VSEG_CACHE   |
131                      VSEG_PRIVATE ;
132    }
133    else if( type == VSEG_TYPE_KDATA )
134    {
135        vseg->flags = VSEG_CACHE   |
136                      VSEG_WRITE   ;
137    }
138    else if( type == VSEG_TYPE_KDEV )
139    {
140        vseg->flags = VSEG_WRITE   ;
141    }
[18]142    else
[1]143    {
[492]144            assert( false , "illegal vseg type\n" );
[18]145    }
[1]146
[315]147}  // end vseg_init()
148
[1]149//////////////////////////////////////////
150void vseg_init_from_ref( vseg_t    * vseg,
[407]151                         xptr_t      ref_xp )
[1]152{
153    // get remote vseg cluster and pointer
[407]154    cxy_t    cxy = (cxy_t   )GET_CXY( ref_xp );
155    vseg_t * ptr = (vseg_t *)GET_PTR( ref_xp );
[1]156
157    // initialize vseg with remote_read access
[623]158    vseg->type        =           hal_remote_l32( XPTR( cxy , &ptr->type        ) );
[407]159    vseg->min         = (intptr_t)hal_remote_lpt( XPTR( cxy , &ptr->min         ) );
160    vseg->max         = (intptr_t)hal_remote_lpt( XPTR( cxy , &ptr->max         ) );
[623]161    vseg->vpn_base    =           hal_remote_l32( XPTR( cxy , &ptr->vpn_base    ) );
162    vseg->vpn_size    =           hal_remote_l32( XPTR( cxy , &ptr->vpn_size    ) );
163    vseg->flags       =           hal_remote_l32( XPTR( cxy , &ptr->flags       ) );
164    vseg->file_offset =           hal_remote_l32( XPTR( cxy , &ptr->file_offset ) );
165    vseg->file_size   =           hal_remote_l32( XPTR( cxy , &ptr->file_size   ) );
[567]166        vseg->mapper_xp   = (xptr_t)  hal_remote_l64( XPTR( cxy , &ptr->mapper_xp   ) );
[453]167
168    switch (vseg->type)
169    {
[623]170        case VSEG_TYPE_DATA:      // unused
[457]171        {
[453]172            vseg->cxy = 0xffff;
173            break;
174        }
[623]175        case VSEG_TYPE_CODE:      // always local
[457]176        case VSEG_TYPE_STACK: 
[623]177        case VSEG_TYPE_KCODE:
[457]178        {
[453]179            vseg->cxy = local_cxy;
180            break;
181        }
[623]182        case VSEG_TYPE_ANON:      // intrinsic
[453]183        case VSEG_TYPE_FILE:
[457]184        case VSEG_TYPE_REMOTE: 
[623]185        case VSEG_TYPE_KDEV:
186        case VSEG_TYPE_KDATA:
[457]187        {
[567]188            vseg->cxy = (cxy_t) hal_remote_l32( XPTR(cxy, &ptr->cxy) );
[453]189            break;
190        }
[457]191        default: 
192        {
[492]193            assert( false, "Illegal vseg type" );
[453]194            break;
195        }
196    }
[184]197}
[1]198
199
Note: See TracBrowser for help on using the repository browser.