Changeset 567 for trunk/kernel/mm/ppm.c


Ignore:
Timestamp:
Oct 5, 2018, 12:01:52 AM (4 years ago)
Author:
alain
Message:

Complete restructuration of kernel locks.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/kernel/mm/ppm.c

    r551 r567  
    33 *
    44 * Authors  Ghassan Almaless (2008,2009,2010,2011,2012)
    5  *          Alain Greiner    (2016,2017)
     5 *          Alain Greiner    (2016,2017,2018)
    66 *
    77 * Copyright (c) UPMC Sorbonne Universites
     
    3030#include <bits.h>
    3131#include <page.h>
    32 #include <spinlock.h>
     32#include <busylock.h>
     33#include <queuelock.h>
    3334#include <thread.h>
    3435#include <cluster.h>
    3536#include <kmem.h>
    3637#include <process.h>
    37 #include <dqdt.h>
     38#include <mapper.h>
    3839#include <ppm.h>
     40
     41////////////////////////////////////////////////////////////////////////////////////////
     42//     functions to  translate [ page <-> base <-> ppn ]
     43////////////////////////////////////////////////////////////////////////////////////////
    3944
    4045////////////////////////////////////////////////
     
    4651}
    4752
    48 
    49 
    5053/////////////////////////////////////////////
    5154inline xptr_t ppm_page2base( xptr_t page_xp )
     
    139142
    140143
     144////////////////////////////////////////////////////////////////////////////////////////
     145//     functions to  allocate / release  physical pages
     146////////////////////////////////////////////////////////////////////////////////////////
    141147
    142148///////////////////////////////////////////
     
    204210uint32_t cycle = (uint32_t)hal_get_cycles();
    205211if( DEBUG_PPM_ALLOC_PAGES < cycle )
    206 printk("\n[DBG] in %s : thread %x enter for %d page(s) / cycle %d\n",
    207 __FUNCTION__ , CURRENT_THREAD , 1<<order, cycle );
     212printk("\n[DBG] in %s : thread %x in process %x enter for %d page(s) / cycle %d\n",
     213__FUNCTION__, CURRENT_THREAD->trdid, CURRENT_THREAD->process->pid, 1<<order, cycle );
    208214#endif
    209215
     
    221227
    222228        // take lock protecting free lists
    223         uint32_t       irq_state;
    224         spinlock_lock_busy( &ppm->free_lock, &irq_state );
     229        busylock_acquire( &ppm->free_lock );
    225230
    226231        // find a free block equal or larger to requested size
     
    238243        {
    239244                // release lock protecting free lists
    240                 spinlock_unlock_busy( &ppm->free_lock, irq_state );
     245                busylock_release( &ppm->free_lock );
    241246
    242247#if DEBUG_PPM_ALLOC_PAGES
    243248cycle = (uint32_t)hal_get_cycles();
    244249if( DEBUG_PPM_ALLOC_PAGES < cycle )
    245 printk("\n[DBG] in %s : thread %x cannot allocate %d page(s) at cycle %d\n",
    246 __FUNCTION__ , CURRENT_THREAD , 1<<order, cycle );
     250printk("\n[DBG] in %s : thread %x in process %x cannot allocate %d page(s) / cycle %d\n",
     251__FUNCTION__, CURRENT_THREAD->trdid, CURRENT_THREAD->process->pid, 1<<order, cycle );
    247252#endif
    248253
     
    274279
    275280        // release lock protecting free lists
    276         spinlock_unlock_busy( &ppm->free_lock, irq_state );
     281        busylock_release( &ppm->free_lock );
    277282
    278283#if DEBUG_PPM_ALLOC_PAGES
    279284cycle = (uint32_t)hal_get_cycles();
    280285if( DEBUG_PPM_ALLOC_PAGES < cycle )
    281 printk("\n[DBG] in %s : thread %x exit / %d page(s) allocated / ppn = %x / cycle %d\n",
    282 __FUNCTION__, CURRENT_THREAD, 1<<order, ppm_page2ppn(XPTR( local_cxy , block )), cycle );
     286printk("\n[DBG] in %s : thread %x in process %x exit for %d page(s) / ppn = %x / cycle %d\n",
     287__FUNCTION__, CURRENT_THREAD->trdid, CURRENT_THREAD->process->pid,
     2881<<order, ppm_page2ppn(XPTR( local_cxy , block )), cycle );
    283289#endif
    284290
     
    296302uint32_t cycle = (uint32_t)hal_get_cycles();
    297303if( DEBUG_PPM_FREE_PAGES < cycle )
    298 printk("\n[DBG] in %s : thread %x enter for %d page(s) / cycle %d\n",
    299 __FUNCTION__ , CURRENT_THREAD , 1<<page->order , cycle );
     304printk("\n[DBG] in %s : thread %x in process %x enter for %d page(s) / ppn %x / cycle %d\n",
     305__FUNCTION__, CURRENT_THREAD->trdid, CURRENT_THREAD->process->pid,
     3061<<page->order, ppm_page2ppn(XPTR(local_cxy , page)), cycle );
    300307#endif
    301308
     
    306313
    307314        // get lock protecting free_pages[] array
    308         spinlock_lock( &ppm->free_lock );
     315        busylock_acquire( &ppm->free_lock );
    309316
    310317        ppm_free_pages_nolock( page );
    311318
    312319        // release lock protecting free_pages[] array
    313         spinlock_unlock( &ppm->free_lock );
     320        busylock_release( &ppm->free_lock );
    314321
    315322#if DEBUG_PPM_FREE_PAGES
    316323cycle = (uint32_t)hal_get_cycles();
    317324if( DEBUG_PPM_FREE_PAGES < cycle )
    318 printk("\n[DBG] in %s : thread %x exit / %d page(s) released / ppn = %x / cycle %d\n",
    319 __FUNCTION__, CURRENT_THREAD, 1<<page->order, ppm_page2ppn(XPTR(local_cxy , page)), cycle );
    320 #endif
    321 
    322 }
    323 
    324 ////////////////
     325printk("\n[DBG] in %s : thread %x in process %x exit for %d page(s) / ppn %x / cycle %d\n",
     326__FUNCTION__, CURRENT_THREAD->trdid, CURRENT_THREAD->process->pid,
     3271<<page->order, ppm_page2ppn(XPTR(local_cxy , page)), cycle );
     328#endif
     329
     330}  // end ppm_free_pages()
     331
     332//////////////////////
    325333void ppm_print( void )
    326334{
     
    332340
    333341        // get lock protecting free lists
    334         spinlock_lock( &ppm->free_lock );
     342        busylock_acquire( &ppm->free_lock );
    335343
    336344        printk("\n***  PPM in cluster %x : %d pages ***\n", local_cxy , ppm->pages_nr );
     
    351359
    352360        // release lock protecting free lists
    353         spinlock_unlock( &ppm->free_lock );
     361        busylock_release( &ppm->free_lock );
    354362}
    355363
     
    368376                {
    369377                        page = LIST_ELEMENT( iter , page_t , list );
    370 
    371378                        if( page->order != order )  return -1;
    372379                }
     
    376383}
    377384
     385
     386//////////////////////////////////////////////////////////////////////////////////////
     387//     functions to handle  dirty physical pages
     388//////////////////////////////////////////////////////////////////////////////////////
     389
     390/////////////////////////////////////////
     391bool_t ppm_page_do_dirty( page_t * page )
     392{
     393        bool_t done = false;
     394
     395        ppm_t * ppm = &LOCAL_CLUSTER->ppm;
     396
     397        // lock the PPM dirty_list
     398        queuelock_acquire( &ppm->dirty_lock );
     399
     400        if( !page_is_flag( page , PG_DIRTY ) )
     401        {
     402                // set dirty flag in page descriptor
     403                page_set_flag( page , PG_DIRTY );
     404
     405                // register page in PPM dirty list
     406                list_add_first( &ppm->dirty_root , &page->list );
     407                done = true;
     408        }
     409
     410        // unlock the PPM dirty_list
     411        queuelock_release( &ppm->dirty_lock );
     412
     413        return done;
     414}
     415
     416///////////////////////////////////////////
     417bool_t ppm_page_undo_dirty( page_t * page )
     418{
     419        bool_t done = false;
     420
     421        ppm_t * ppm = &LOCAL_CLUSTER->ppm;
     422
     423        // lock the dirty_list
     424        queuelock_acquire( &ppm->dirty_lock );
     425
     426        if( page_is_flag( page , PG_DIRTY) )
     427        {
     428                // clear dirty flag in page descriptor
     429                page_clear_flag( page , PG_DIRTY );
     430
     431                // remove page from PPM dirty list
     432                list_unlink( &page->list );
     433                done = true;
     434        }
     435
     436        // unlock the dirty_list
     437        queuelock_release( &ppm->dirty_lock );
     438
     439        return done;
     440}
     441
     442///////////////////////////////
     443void ppm_sync_all_pages( void )
     444{
     445        page_t   * page;
     446        ppm_t    * ppm = &LOCAL_CLUSTER->ppm;
     447
     448        // get the PPM dirty_list lock
     449        queuelock_acquire( &ppm->dirty_lock );
     450
     451        while( !list_is_empty( &ppm->dirty_root ) )
     452        {
     453                page = LIST_FIRST( &ppm->dirty_root ,  page_t , list );
     454
     455                // get the page lock
     456                remote_busylock_acquire( XPTR( local_cxy, &page->lock ) );
     457
     458                // sync the page
     459                vfs_mapper_move_page( page , false );  // from mapper
     460
     461                // release the page lock
     462                remote_busylock_release( XPTR( local_cxy , &page->lock ) );
     463        }
     464
     465        // release the PPM dirty_list lock
     466        queuelock_release( &ppm->dirty_lock );
     467}
     468
Note: See TracChangeset for help on using the changeset viewer.