Index: trunk/kernel/mm/page.h
===================================================================
--- trunk/kernel/mm/page.h	(revision 690)
+++ trunk/kernel/mm/page.h	(revision 1)
@@ -3,5 +3,5 @@
  *
  * Authors Ghassan Almalles (2008,2009,2010,2011,2012)
- *         Alain Greiner    (2016,2017,2018,2019,2020)
+ *         Alain Greiner    (2016)
  *
  * Copyright (c) UPMC Sorbonne Universites
@@ -26,13 +26,15 @@
 #define _PAGE_H_
 
-#include <kernel_config.h>
-#include <hal_kernel_types.h>
-#include <remote_busylock.h>
+#include <almos_config.h>
+#include <hal_types.h>
+#include <spinlock.h>
 #include <list.h>
+#include <slist.h>
+#include <xlist.h>
 
 /***   Forward declarations   ***/
 
 struct mapper_s;
-
+ 
 /*************************************************************************************
  * This  defines the flags that can be attached to a physical page.
@@ -41,35 +43,44 @@
 #define PG_INIT		    0x0001     // page descriptor has been initialised
 #define PG_RESERVED	    0x0002     // cannot be allocated by PPM
-#define PG_FREE		    0x0004     // page not yet allocated by PPM
+#define PG_FREE		    0x0004     // page can be allocated by PPM
+#define PG_INLOAD	    0x0008     // on-going load from disk 
+#define PG_IO_ERR	    0x0010     // mapper signals a read/write access error
+#define PG_BUFFER	    0x0020     // used in blockio.c
 #define PG_DIRTY	    0x0040     // page has been written
-#define PG_COW          0x0080     // page is copy-on-write
+#define PG_LOCKED       0x0080     // page is locked
+
+#define PG_ALL          0xFFFF     // All flags
 
 /*************************************************************************************
  * This structure defines a physical page descriptor.
- * - The remote_busylock is used to allows any remote thread to atomically
- *   test/modify the forks counter or the flags.
- * - The list field is used to register the page in a free list, or in dirty list,
- *   as a given page cannot be simultaneously dirty and free.
- * - The refcount is used to release the page to the PPM.
- * NOTE: the size is 48 bytes for a 32 bits core.
+ * Size is 60 bytes for a 32 bits core...
  ************************************************************************************/
 
 typedef struct page_s
 {
-    uint32_t          flags;          /*! flags defined above                  (4)  */
-    uint32_t          order;          /*! log2( number of small pages)         (4)  */
+    uint16_t          flags;          /*! flags defined above                  (2)  */
+    uint16_t          order;          /*! log2( number of 4Kbytes pages)       (2)  */
+
     struct mapper_s * mapper;         /*! local pointer on associated mapper   (4)  */
     uint32_t          index;          /*! page index in mapper                 (4)  */
-	list_entry_t      list;           /*! for both dirty pages and free pages  (8)  */
-	int32_t           refcount;       /*! references counter for page release  (4)  */
-	uint32_t          forks;          /*! number of pending forks              (4)  */
-	remote_busylock_t lock;           /*! protect forks or flags modifs        (16) */
+ 
+	union                             /*!                                      (4)  */
+	{
+		uint32_t      private;        /*! TODO ??? [AG]                             */
+		void        * data;           /*! TODO ??? [AG]                             */
+		slist_entry_t root;           /*! TODO ??? [AG]                             */
+	};
+
+	list_entry_t      list;           /*! for both dirty pages and free pages  (8)  */ 
+
+    xlist_entry_t     wait_root;      /*! root of list of waiting threads      (16) */
+
+	uint32_t          refcount;       /*! reference counter                    (4)  */
+	spinlock_t        lock;           /*! only used to set the PG_LOCKED flag  (16) */
 }
 page_t;
 
 /*************************************************************************************
- * This function must be called by a thread running in the local cluster.
- * It initializes the page descriptor.
- *************************************************************************************
+ * This function initializes one page descriptor.
  * @ page    : pointer to page descriptor
  ************************************************************************************/
@@ -77,38 +88,60 @@
 
 /*************************************************************************************
- * This function must be called by a thread running in the local cluster.
- * It atomically set one or several flags in page descriptor flags.
- *************************************************************************************
+ * This function set one or several flags in page descriptor flags.
  * @ page    : pointer to page descriptor.
- * @ value   : all non zero bits in value will be set.
+ * @ value   : all non zero bits in value will be set. 
  ************************************************************************************/
 inline void page_set_flag( page_t   * page,
-                           uint32_t   value );
+                           uint16_t   value );
 
 /*************************************************************************************
- * This function must be called by a thread running in the local cluster.
- * It atomically reset one or several flags in page descriptor flags.
- *************************************************************************************
+ * This function reset one or several flags in page descriptor flags.
  * @ page    : pointer to page descriptor.
- * @ value   : all non zero bits in value will be cleared.
+ * @ value   : all non zero bits in value will be cleared. 
  ************************************************************************************/
 inline void page_clear_flag( page_t   * page,
-                             uint32_t   value );
+                             uint16_t   value );
 
 /*************************************************************************************
- * This function must be called by a thread running in the local cluster.
- * It tests the value of one or several flags in page descriptor flags.
- *************************************************************************************
+ * This function test the value of one or several flags in page descriptor flags.
  * @ page    : pointer to page descriptor.
  * @ value   : all non zero bits will be tested.
- * @ returns true if at least one non zero bit in value is set / false otherwise.
+ * @ returns true if at least one non zero bit in value is set / false otherwise. 
  ************************************************************************************/
 inline bool_t page_is_flag( page_t   * page,
-                            uint32_t   value );
+                            uint16_t   value );
 
 /*************************************************************************************
- * This function must be called by a thread running in the local cluster.
- * It resets to 0 all bytes in a given page.
- *************************************************************************************
+ * This function synchronizes (i.e. update the disk) all dirty pages in a cluster.
+ * It scan the PPM dirty list, that should be empty when this operation is completed. 
+ ************************************************************************************/
+void sync_all_pages();
+
+/*************************************************************************************
+ * This function set the PG_DIRTY flag in the page descriptor,
+ * and register the page in the dirty list in PPM.
+ * @ page     : pointer on page descriptor.
+ * @ returns true if page was not dirty / returns false if page was dirty
+ ************************************************************************************/
+bool_t page_do_dirty( page_t * page );
+
+/*************************************************************************************
+ * This function reset the PG_DIRTY flag in the page descriptor,
+ * and remove the page from the dirty list in PPM.
+ * @ page     : pointer on page descriptor.
+ * @ returns true if page was dirty / returns false if page was not dirty 
+ ************************************************************************************/
+bool_t page_undo_dirty( page_t * page );
+
+/*************************************************************************************
+ * This function makes a local copy of the content of a src page  to a dst page.
+ * @ dst      : pointer on destination page descriptor.
+ * @ src      : pointer on source page descriptor.
+ ************************************************************************************/
+void page_copy( page_t * dst,
+                page_t * src );
+
+/*************************************************************************************
+ * This function reset to 0 all bytes in a given page. 
  * @ page     : pointer on page descriptor.
  ************************************************************************************/
@@ -116,7 +149,21 @@
 
 /*************************************************************************************
- * This function must be called by a thread running in the local cluster.
- * It atomically increments the page refcount.
- *************************************************************************************
+ * This blocking function set the PG_LOCKED flag on the page.
+ * It deschedule if the page has already been locked by another thread,
+ * and returns only when the flag has been successfully set. 
+ * @ page     : pointer on page descriptor.
+ ************************************************************************************/
+void page_lock( page_t * page );
+
+/*************************************************************************************
+ * This blocking function reset the PG_LOCKED flag on the page, if there is no
+ * other waiting thread. IF there is waiting thread(s), it activates the first
+ * waiting thread without modifying the PG_LOCKED flag.
+ * @ page     : pointer on page descriptor.
+ ************************************************************************************/
+void page_unlock( page_t * page );
+
+/*************************************************************************************
+ * This blocking function atomically increment the page refcount.
  * @ page     : pointer on page descriptor.
  ************************************************************************************/
@@ -124,82 +171,14 @@
 
 /*************************************************************************************
- * This function must be called by a thread running in the local cluster.
- * It atomically decrements the page refcount.
- *************************************************************************************
+ * This blocking function atomically decrement the page refcount.
  * @ page     : pointer on page descriptor.
  ************************************************************************************/
 inline void page_refcount_down( page_t * page );
 
+/*************************************************************************************
+ * This function display the values contained in a page descriptor.
+ ************************************************************************************/
+void page_print( page_t * page );
 
 
-
-
-/*************************************************************************************
- * This function must be called by a thread running in the local cluster.
- * It initializes the page descriptor.
- *************************************************************************************
- * @ page_xp    : extended pointer to page descriptor.
- ************************************************************************************/
-inline void page_remote_init( xptr_t  page_xp );
-
-/*************************************************************************************
- * This function can be called by any thread running in any cluster.
- * It atomically set one or several flags in a remote page descriptor
- * identified by the <page_xp> argument.
- *************************************************************************************
- * @ page_xp : extended pointer to page descriptor.
- * @ value   : all non zero bits in value will be set.
- ************************************************************************************/
-inline void page_remote_set_flag( xptr_t    page_xp,
-                                  uint32_t  value );
-
-/*************************************************************************************
- * This function can be called by any thread running in any cluster.
- * It atomically reset one or several flags in a remote page descriptor
- * identified by the <page_xp> argument.
- *************************************************************************************
- * @ page_xp : extended pointer to page descriptor.
- * @ value   : all non zero bits in value will be cleared.
- ************************************************************************************/
-inline void page_remote_clear_flag( xptr_t    page_xp,
-                                    uint32_t  value );
-
-/*************************************************************************************
- * This function can be called by any thread running in any cluster.
- * It tests the value of one or several flags in a remote page descriptor
- * identified by the <page_xp> argument.
- *************************************************************************************
- * @ page_xp : extended pointer to page descriptor.
- * @ value   : all non zero bits will be tested.
- * @ returns true if at least one non zero bit in value is set / false otherwise.
- ************************************************************************************/
-inline bool_t page_remote_is_flag( xptr_t    page_xp,
-                                   uint32_t  value );
-
-/*************************************************************************************
- * This function can be called by any thread running in any cluster.
- * It atomically increments the refcount for the remote page identified by
- * the <page_xp> argument.
- *************************************************************************************
- * @ page_xp   : extended pointer on page descriptor.
- ************************************************************************************/
-inline void page_remote_refcount_up( xptr_t page_xp );
-
-/*************************************************************************************
- * This function can be called by any thread running in any cluster.
- * It atomically decrements the refcount for the remote page identified by
- * the <page_xp> argument.
- *************************************************************************************
- * @ page_xp   : extended pointer on page descriptor.
- ************************************************************************************/
-inline void page_remote_refcount_down( xptr_t  page_xp );
-
-/*************************************************************************************
- * This debug function can be called by any thread running in any cluster.
- * It displays the values contained in a page descriptor.
- *************************************************************************************
- * @ page_xp     : extended pointer on page descriptor.
- ************************************************************************************/
-void page_remote_display( xptr_t  page_xp );
-
 #endif	/* _PAGE_H_ */
