source: trunk/kernel/kern/rpc.c @ 640

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

Remove all RPCs in page-fault handling.

File size: 99.6 KB
Line 
1/*
2 * rpc.c - RPC operations implementation.
3 *
4 * Author    Alain Greiner (2016,2017,2018,2019)
5 *
6 * Copyright (c)  UPMC Sorbonne Universites
7 *
8 * This file is part of ALMOS-MKH.
9 *
10 * ALMOS-MKH is free software; you can redistribute it and/or modify it
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 *
14 * ALMOS-MKH is distributed in the hope that it will be useful, but
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
20 * along with ALMOS-MKH; if not, write to the Free Software Foundation,
21 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
22 */
23
24#include <kernel_config.h>
25#include <hal_kernel_types.h>
26#include <hal_vmm.h>
27#include <hal_atomic.h>
28#include <hal_remote.h>
29#include <hal_irqmask.h>
30#include <hal_special.h>
31#include <printk.h>
32#include <user_dir.h>
33#include <remote_sem.h>
34#include <core.h>
35#include <mapper.h>
36#include <chdev.h>
37#include <bits.h>
38#include <thread.h>
39#include <cluster.h>
40#include <process.h>
41#include <vfs.h>
42#include <fatfs.h>
43#include <rpc.h>
44
45
46/////////////////////////////////////////////////////////////////////////////////////////
47// Array of function pointers and array of printable strings.
48// These arrays must be kept consistent with enum in rpc.h file.
49/////////////////////////////////////////////////////////////////////////////////////////
50
51rpc_server_t * rpc_server[RPC_MAX_INDEX] =
52{
53    &rpc_undefined,                        // 0
54    &rpc_undefined,                        // 1
55    &rpc_undefined,                        // 2
56    &rpc_process_make_fork_server,         // 3
57    &rpc_user_dir_create_server,           // 4
58    &rpc_user_dir_destroy_server,          // 5
59    &rpc_thread_user_create_server,        // 6
60    &rpc_thread_kernel_create_server,      // 7
61    &rpc_vfs_fs_update_dentry_server,      // 8
62    &rpc_process_sigaction_server,         // 9
63
64    &rpc_vfs_inode_create_server,          // 10 
65    &rpc_vfs_inode_destroy_server,         // 11 
66    &rpc_vfs_dentry_create_server,         // 12 
67    &rpc_vfs_dentry_destroy_server,        // 13 
68    &rpc_vfs_file_create_server,           // 14
69    &rpc_vfs_file_destroy_server,          // 15
70    &rpc_vfs_fs_new_dentry_server,         // 16
71    &rpc_vfs_fs_add_dentry_server,         // 17
72    &rpc_vfs_fs_remove_dentry_server,      // 18
73    &rpc_vfs_inode_load_all_pages_server,  // 19
74
75    &rpc_undefined,                        // 20
76    &rpc_undefined,                        // 21
77    &rpc_undefined,                        // 22
78    &rpc_undefined,                        // 23
79    &rpc_mapper_sync_server,               // 24
80    &rpc_vmm_resize_vseg_server,           // 25
81    &rpc_vmm_remove_vseg_server,           // 26
82    &rpc_vmm_create_vseg_server,           // 27
83    &rpc_vmm_set_cow_server,               // 28
84    &rpc_undefined,                        // 29
85};
86
87char * rpc_str[RPC_MAX_INDEX] =
88{
89    "undefined_0",               // 0
90    "undefined_1",               // 1
91    "undefined_2",               // 2
92    "PROCESS_MAKE_FORK",         // 3
93    "USER_DIR_CREATE",           // 4
94    "USER_DIR_DESTROY",          // 5
95    "THREAD_USER_CREATE",        // 6
96    "THREAD_KERNEL_CREATE",      // 7
97    "VFS_FS_UPDATE_DENTRY",      // 8
98    "PROCESS_SIGACTION",         // 9
99
100    "VFS_INODE_CREATE",          // 10
101    "VFS_INODE_DESTROY",         // 11
102    "VFS_DENTRY_CREATE",         // 12
103    "VFS_DENTRY_DESTROY",        // 13
104    "VFS_FILE_CREATE",           // 14
105    "VFS_FILE_DESTROY",          // 15
106    "VFS_FS_NEW_DENTRY",         // 16
107    "VFS_FS_ADD_DENTRY",         // 17
108    "VFS_FS_REMOVE_DENTRY",      // 18
109    "VFS_INODE_LOAD_ALL_PAGES",  // 19
110
111    "VMM_GLOBAL_RESIZE_VSEG",    // 20
112    "VMM_GLOBAL_UPDATE_PTE",     // 21
113    "undefined_22",              // 22
114    "undefined_23",              // 23
115    "MAPPER_SYNC",               // 24
116    "undefined_25",              // 25
117    "VMM_REMOVE_VSEG",           // 26
118    "VMM_CREATE_VSEG",           // 27
119    "VMM_SET_COW",               // 28
120    "undefined_29",              // 29
121};
122
123//////////////////////////////////////////////////////////////////////////////////
124void __attribute__((noinline)) rpc_undefined( xptr_t xp __attribute__ ((unused)) )
125{
126        assert( false , "called in cluster %x", local_cxy );
127}
128
129/***************************************************************************************/
130/************ Generic function supporting RPCs : client side ***************************/
131/***************************************************************************************/
132
133///////////////////////////////////////
134void rpc_send( cxy_t        server_cxy, 
135               rpc_desc_t * rpc )
136{
137    lid_t              server_core_lid;
138    lid_t              client_core_lid;
139    volatile error_t   full;
140    thread_t         * this;
141
142    full            = 0;
143    this            = CURRENT_THREAD;
144    client_core_lid = this->core->lid;
145
146    // check calling thread can yield when is not the IDLE thread
147    // RPCs executed by the IDLE thread during kernel_init do not deschedule
148    if( this->type != THREAD_IDLE ) thread_assert_can_yield( this , __FUNCTION__ );
149
150    // select a server_core : use client core index if possible / core 0 otherwise
151    if( client_core_lid < hal_remote_l32( XPTR( server_cxy , &LOCAL_CLUSTER->cores_nr ) ) )
152    {
153        server_core_lid = client_core_lid;
154    }
155    else
156    {   
157        server_core_lid = 0;
158    }
159
160    // register client_thread and client_core in RPC descriptor
161    rpc->thread = this;
162    rpc->lid    = client_core_lid;
163
164    // build extended pointer on the RPC descriptor
165        xptr_t   desc_xp = XPTR( local_cxy , rpc );
166
167    // get local pointer on rpc_fifo in remote cluster,
168    remote_fifo_t * rpc_fifo    = &LOCAL_CLUSTER->rpc_fifo[server_core_lid];
169    xptr_t          rpc_fifo_xp = XPTR( server_cxy , rpc_fifo );
170
171        // post RPC in remote fifo / deschedule without blocking if fifo full
172    do
173    { 
174        full = remote_fifo_put_item( rpc_fifo_xp , (uint64_t )desc_xp );
175
176            if ( full ) 
177        {
178            printk("\n[WARNING] %s : cluster %x cannot post RPC to cluster %x\n",
179            __FUNCTION__ , local_cxy , server_cxy );
180
181            // deschedule without blocking
182            sched_yield("RPC fifo full");
183        }
184    }
185    while( full );
186 
187#if DEBUG_RPC_CLIENT_GENERIC
188uint32_t cycle = (uint32_t)hal_get_cycles();
189uint32_t items = remote_fifo_items( rpc_fifo_xp );
190if( DEBUG_RPC_CLIENT_GENERIC < cycle ) 
191printk("\n[%s] thread[%x,%x] / rpc %s / server[%x,%d] / items %d / cycle %d\n",
192__FUNCTION__, this->process->pid, this->trdid, rpc_str[rpc->index], 
193server_cxy, server_core_lid, items, cycle );
194#endif
195       
196   // send IPI to the selected server core
197   dev_pic_send_ipi( server_cxy , server_core_lid );
198
199    // wait RPC completion before returning if blocking RPC :
200    // - deschedule without blocking if thread idle (in kernel init)
201    // - block and deschedule policy for any other thread
202    if ( rpc->blocking )
203    {
204        if( this->type == THREAD_IDLE )  // deschedule without blocking policy
205        {
206 
207#if DEBUG_RPC_CLIENT_GENERIC
208cycle = (uint32_t)hal_get_cycles();
209if( DEBUG_RPC_CLIENT_GENERIC < cycle ) 
210printk("\n[%s] thread[%x,%x] enter waiting loop for rpc %s / cycle %d\n",
211__FUNCTION__, this->process->pid, this->trdid, rpc_str[rpc->index], cycle );
212#endif
213             while( 1 )
214             {
215                 // check responses counter
216                 if( hal_remote_l32( XPTR( local_cxy , rpc->rsp ) ) == 0 ) break;
217                   
218                 // deschedule
219                 sched_yield("busy_waiting RPC completion");
220             }
221
222#if DEBUG_RPC_CLIENT_GENERIC
223cycle = (uint32_t)hal_get_cycles();
224if( DEBUG_RPC_CLIENT_GENERIC < cycle ) 
225printk("\n[%s] thread[%x,%x] received response for rpc %s / cycle %d\n",
226__FUNCTION__, this->process->pid, this->trdid, rpc_str[rpc->index], cycle );
227#endif
228 
229        }
230        else                            // block and deschedule policy
231        {
232
233#if DEBUG_RPC_CLIENT_GENERIC
234cycle = (uint32_t)hal_get_cycles();
235if( DEBUG_RPC_CLIENT_GENERIC < cycle ) 
236printk("\n[%s] thread[%x,%x] blocks & deschedules for rpc %s / cycle %d\n",
237__FUNCTION__, this->process->pid, this->trdid, rpc_str[rpc->index], cycle );
238#endif
239
240        // block client thread
241        thread_block( XPTR( local_cxy , this ) , THREAD_BLOCKED_RPC );
242
243        // deschedule
244        sched_yield("blocked on RPC");
245
246#if DEBUG_RPC_CLIENT_GENERIC
247cycle = (uint32_t)hal_get_cycles();
248if( DEBUG_RPC_CLIENT_GENERIC < cycle ) 
249printk("\n[%s] thread[%x,%x] resumes after rpc %s / cycle %d\n",
250__FUNCTION__, this->process->pid, this->trdid, rpc_str[rpc->index], cycle );
251#endif
252        }
253
254// response must be available for a blocking RPC
255assert( (*rpc->rsp == 0) , "illegal response for RPC %s\n", rpc_str[rpc->index] );
256
257    }
258    else       // non blocking RPC
259    {
260
261#if DEBUG_RPC_CLIENT_GENERIC
262cycle = (uint32_t)hal_get_cycles();
263if( DEBUG_RPC_CLIENT_GENERIC < cycle ) 
264printk("\n[%s] thread[%x,%x] returns for non blocking rpc %s / cycle %d\n",
265__FUNCTION__, this->process->pid, this->trdid, rpc_str[rpc->index], cycle );
266#endif
267
268    }
269}  // end rpc_send()
270
271
272/***************************************************************************************/
273/************ Generic functions supporting RPCs : server side **************************/
274/***************************************************************************************/
275
276////////////////////////////
277void rpc_server_func( void )
278{
279    error_t         empty;              // local RPC fifo state
280    xptr_t          desc_xp;            // extended pointer on RPC request
281    cxy_t           desc_cxy;           // RPC request cluster (client)
282    rpc_desc_t    * desc_ptr;           // RPC request local pointer
283    uint32_t        index;              // RPC request index
284    thread_t      * client_ptr;         // local pointer on client thread
285    xptr_t          client_xp;          // extended pointer on client thread
286    lid_t           client_lid;         // local index of client core
287        thread_t      * server_ptr;         // local pointer on server thread
288    xptr_t          server_xp;          // extended pointer on server thread
289    lid_t           server_lid;         // local index of server core
290        remote_fifo_t * rpc_fifo;           // local pointer on RPC fifo
291    uint32_t      * rsp_ptr;            // local pointer on responses counter
292    xptr_t          rsp_xp;             // extended pointer on responses counter
293    uint32_t        responses;          // number of expected responses
294
295    // makes RPC thread not preemptable
296        hal_disable_irq( NULL );
297 
298        server_ptr      = CURRENT_THREAD;
299    server_xp       = XPTR( local_cxy , server_ptr );
300    server_lid      = server_ptr->core->lid;
301        rpc_fifo        = &LOCAL_CLUSTER->rpc_fifo[server_lid];
302
303    // "infinite" RPC thread loop
304        while(1)
305        {
306        // try to take RPC_FIFO ownership
307        if( hal_atomic_test_set( &rpc_fifo->owner , server_ptr->trdid ) ) 
308        {
309
310#if DEBUG_RPC_SERVER_GENERIC
311uint32_t cycle = (uint32_t)hal_get_cycles();
312if( DEBUG_RPC_SERVER_GENERIC < cycle ) 
313printk("\n[%s] RPC thread[%x,%x] on core[%d] takes RPC_FIFO ownership / cycle %d\n",
314__FUNCTION__, server_ptr->process->pid, server_ptr->trdid, server_lid, cycle );
315#endif
316                // try to consume one RPC request 
317                empty = remote_fifo_get_item( rpc_fifo , (uint64_t *)&desc_xp );
318
319            // release RPC_FIFO ownership
320            rpc_fifo->owner = 0;
321
322            // handle RPC request if success
323                if ( empty == 0 )   
324            {
325                // get client cluster and pointer on RPC descriptor
326                desc_cxy = GET_CXY( desc_xp );
327                desc_ptr = GET_PTR( desc_xp );
328
329                // get relevant infos from RPC descriptor
330                    index      = hal_remote_l32( XPTR( desc_cxy , &desc_ptr->index ) );
331                client_ptr = hal_remote_lpt( XPTR( desc_cxy , &desc_ptr->thread ) );
332                rsp_ptr    = hal_remote_lpt( XPTR( desc_cxy , &desc_ptr->rsp ) );
333                client_lid = hal_remote_l32( XPTR( desc_cxy , &desc_ptr->lid ) );
334
335                rsp_xp     = XPTR( desc_cxy , rsp_ptr );
336                client_xp  = XPTR( desc_cxy , client_ptr );
337
338#if DEBUG_RPC_SERVER_GENERIC
339cycle = (uint32_t)hal_get_cycles();
340uint32_t items = remote_fifo_items( XPTR( local_cxy , rpc_fifo ) );
341if( DEBUG_RPC_SERVER_GENERIC < cycle ) 
342printk("\n[%s] RPC thread[%x,%x] got rpc %s / client_cxy %x / items %d / cycle %d\n",
343__FUNCTION__, server_ptr->process->pid, server_ptr->trdid, rpc_str[index], desc_cxy, items, cycle );
344#endif
345                // register client thread in RPC thread descriptor
346                server_ptr->rpc_client_xp = client_xp;
347 
348                // call the relevant server function
349                rpc_server[index]( desc_xp );
350
351#if DEBUG_RPC_SERVER_GENERIC
352cycle = (uint32_t)hal_get_cycles();
353if( DEBUG_RPC_SERVER_GENERIC < cycle ) 
354printk("\n[%s] RPC thread[%x,%x] completes rpc %s / client_cxy %x / cycle %d\n",
355__FUNCTION__, server_ptr->process->pid, server_ptr->trdid, rpc_str[index], desc_cxy, cycle );
356#endif
357                // decrement expected responses counter
358                responses = hal_remote_atomic_add( rsp_xp , -1 );
359
360                // unblock client thread if last response
361                if( responses == 1 ) 
362                {
363                    // unblock client thread
364                    thread_unblock( client_xp , THREAD_BLOCKED_RPC );
365
366                    hal_fence();
367
368#if DEBUG_RPC_SERVER_GENERIC
369cycle = (uint32_t)hal_get_cycles();
370trdid_t     client_trdid = hal_remote_l32( XPTR( desc_cxy , &client_ptr->trdid ) );
371process_t * process      = hal_remote_lpt( XPTR( desc_cxy , &client_ptr->process ) );
372pid_t       client_pid   = hal_remote_l32( XPTR( desc_cxy , &process->pid ) );
373if( DEBUG_RPC_SERVER_GENERIC < cycle ) 
374printk("\n[%s] RPC thread[%x,%x] unblocked client thread[%x,%x] / cycle %d\n",
375__FUNCTION__, server_ptr->process->pid, server_ptr->trdid,
376client_pid, client_trdid, cycle );
377#endif
378                    // send IPI to client core
379                    dev_pic_send_ipi( desc_cxy , client_lid );
380                }
381            }  // end RPC handling if fifo non empty
382        }  // end if RPC_fIFO ownership successfully taken and released
383
384        // sucide if too many RPC threads
385        if( LOCAL_CLUSTER->rpc_threads[server_lid] >= CONFIG_RPC_THREADS_MAX )
386            {
387
388#if DEBUG_RPC_SERVER_GENERIC
389uint32_t cycle = (uint32_t)hal_get_cycles();
390if( DEBUG_RPC_SERVER_GENERIC < cycle ) 
391printk("\n[%s] RPC thread[%x,%x] suicides / cycle %d\n",
392__FUNCTION__, server_ptr->process->pid, server_ptr->trdid, cycle );
393#endif
394            // update RPC threads counter
395                hal_atomic_add( &LOCAL_CLUSTER->rpc_threads[server_lid] , -1 );
396
397            // RPC thread blocks on GLOBAL
398                thread_block( server_xp , THREAD_BLOCKED_GLOBAL );
399
400            // RPC thread set the REQ_DELETE flag to suicide
401            hal_remote_atomic_or( server_xp , THREAD_FLAG_REQ_DELETE );
402            }
403        // block and deschedule otherwise
404        else
405        {
406
407#if DEBUG_RPC_SERVER_GENERIC
408uint32_t cycle = (uint32_t)hal_get_cycles();
409if( DEBUG_RPC_SERVER_GENERIC < cycle ) 
410printk("\n[%s] RPC thread[%x,%x] blocks & deschedules / cycle %d\n",
411__FUNCTION__, server_ptr->process->pid, server_ptr->trdid, cycle );
412#endif
413            // RPC thread blocks on IDLE
414            thread_block( server_xp , THREAD_BLOCKED_IDLE );
415
416            // RPC thread deschedules
417            sched_yield("RPC_FIFO empty");
418        }
419        } // end infinite loop
420
421} // end rpc_server_func()
422
423
424/////////////////////////////////////////////////////////////////////////////////////////
425// [0]       RPC_PMEM_GET_PAGES deprecated [AG] May 2019
426/////////////////////////////////////////////////////////////////////////////////////////
427
428/*
429///////////////////////////////////////////////
430void rpc_pmem_get_pages_client( cxy_t      cxy,
431                                uint32_t   order,      // in
432                                page_t  ** page )      // out
433{
434#if DEBUG_RPC_PMEM_GET_PAGES
435thread_t * this = CURRENT_THREAD;
436uint32_t cycle = (uint32_t)hal_get_cycles();
437if( cycle > DEBUG_RPC_PMEM_GET_PAGES )
438printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
439__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
440#endif
441
442    uint32_t responses = 1;
443
444    // initialise RPC descriptor header
445    rpc_desc_t  rpc;
446    rpc.index     = RPC_PMEM_GET_PAGES;
447    rpc.blocking  = true;
448    rpc.rsp       = &responses;
449
450    // set input arguments in RPC descriptor
451    rpc.args[0] = (uint64_t)order;
452
453    // register RPC request in remote RPC fifo
454    rpc_send( cxy , &rpc );
455
456    // get output arguments from RPC descriptor
457    *page = (page_t *)(intptr_t)rpc.args[1];
458
459#if DEBUG_RPC_PMEM_GET_PAGES
460cycle = (uint32_t)hal_get_cycles();
461if( cycle > DEBUG_RPC_PMEM_GET_PAGES )
462printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
463__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
464#endif
465}
466
467///////////////////////////////////////////
468void rpc_pmem_get_pages_server( xptr_t xp )
469{
470#if DEBUG_RPC_PMEM_GET_PAGES
471thread_t * this = CURRENT_THREAD;
472uint32_t cycle = (uint32_t)hal_get_cycles();
473if( cycle > DEBUG_RPC_PMEM_GET_PAGES )
474printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
475__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
476#endif
477
478    // get client cluster identifier and pointer on RPC descriptor
479    cxy_t        cxy  = GET_CXY( xp );
480    rpc_desc_t * desc = GET_PTR( xp );
481
482    // get input arguments from client RPC descriptor
483    uint32_t order = (uint32_t)hal_remote_l64( XPTR( cxy , &desc->args[0] ) );
484   
485    // call local pmem allocator
486    page_t * page = ppm_alloc_pages( order );
487
488    // set output arguments into client RPC descriptor
489    hal_remote_s64( XPTR( cxy , &desc->args[1] ) , (uint64_t)(intptr_t)page );
490
491#if DEBUG_RPC_PMEM_GET_PAGES
492cycle = (uint32_t)hal_get_cycles();
493if( cycle > DEBUG_RPC_PMEM_GET_PAGES )
494printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
495__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
496#endif
497}
498*/
499
500/////////////////////////////////////////////////////////////////////////////////////////
501// [1]       RPC_PMEM_RELEASE_PAGES deprecated [AG] may 2019
502/////////////////////////////////////////////////////////////////////////////////////////
503
504/*
505//////////////////////////////////////////////////
506void rpc_pmem_release_pages_client( cxy_t     cxy,
507                                    page_t  * page )      // out
508{
509#if DEBUG_RPC_PMEM_RELEASE_PAGES
510thread_t * this = CURRENT_THREAD;
511uint32_t cycle = (uint32_t)hal_get_cycles();
512if( cycle > DEBUG_RPC_PMEM_RELEASE_PAGES )
513printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
514__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
515#endif
516
517    uint32_t responses = 1;
518
519    // initialise RPC descriptor header
520    rpc_desc_t  rpc;
521    rpc.index    = RPC_PMEM_RELEASE_PAGES;
522    rpc.blocking = true;
523    rpc.rsp      = &responses;
524
525    // set input arguments in RPC descriptor
526    rpc.args[0] = (uint64_t)(intptr_t)page;
527
528    // register RPC request in remote RPC fifo
529    rpc_send( cxy , &rpc );
530
531#if DEBUG_RPC_PMEM_RELEASE_PAGES
532cycle = (uint32_t)hal_get_cycles();
533if( cycle > DEBUG_RPC_PMEM_RELEASE_PAGES )
534printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
535__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
536#endif
537}
538
539///////////////////////////////////////////////
540void rpc_pmem_release_pages_server( xptr_t xp )
541{
542#if DEBUG_RPC_PMEM_RELEASE_PAGES
543thread_t * this = CURRENT_THREAD;
544uint32_t cycle = (uint32_t)hal_get_cycles();
545if( cycle > DEBUG_RPC_PMEM_RELEASE_PAGES )
546printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
547__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
548#endif
549
550    // get client cluster identifier and pointer on RPC descriptor
551    cxy_t        cxy  = GET_CXY( xp );
552    rpc_desc_t * desc = GET_PTR( xp );
553
554    // get input arguments from client RPC descriptor
555    page_t * page = (page_t *)(intptr_t)hal_remote_l64( XPTR( cxy , &desc->args[0] ) );
556   
557    // release memory to local pmem
558    kmem_req_t req;
559    req.type = KMEM_PPM;
560    req.ptr  = page;
561    kmem_free( &req );
562
563#if DEBUG_RPC_PMEM_RELEASE_PAGES
564cycle = (uint32_t)hal_get_cycles();
565if( cycle > DEBUG_RPC_PMEM_RELEASE_PAGES )
566printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
567__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
568#endif
569}
570*/
571
572/////////////////////////////////////////////////////////////////////////////////////////
573// [2]          RPC_PPM_DISPLAY deprecated [AG] May 2019   
574/////////////////////////////////////////////////////////////////////////////////////////
575
576/*
577/////////////////////////////////////////
578void rpc_ppm_display_client( cxy_t  cxy )
579{
580#if DEBUG_RPC_PPM_DISPLAY
581thread_t * this = CURRENT_THREAD;
582uint32_t cycle = (uint32_t)hal_get_cycles();
583if( cycle > DEBUG_RPC_PPM_DISPLAY )
584printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
585__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
586#endif
587
588    uint32_t responses = 1;
589
590    // initialise RPC descriptor header
591    rpc_desc_t  rpc;
592    rpc.index    = RPC_PPM_DISPLAY;
593    rpc.blocking = true;
594    rpc.rsp      = &responses;
595
596    // register RPC request in remote RPC fifo
597    rpc_send( cxy , &rpc );
598
599#if DEBUG_RPC_PPM_DISPLAY
600cycle = (uint32_t)hal_get_cycles();
601if( cycle > DEBUG_RPC_PPM_DISPLAY )
602printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
603__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
604#endif
605}
606
607////////////////////////////////////////////////////////////////////
608void rpc_ppm_display_server( xptr_t __attribute__((__unused__)) xp )
609{
610#if DEBUG_RPC_PPM_DISPLAY
611thread_t * this = CURRENT_THREAD;
612uint32_t cycle = (uint32_t)hal_get_cycles();
613if( cycle > DEBUG_RPC_PPM_DISPLAY )
614printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
615__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
616#endif
617
618    // call local kernel function
619    ppm_display();
620
621#if DEBUG_RPC_PPM_DISPLAY
622cycle = (uint32_t)hal_get_cycles();
623if( cycle > DEBUG_RPC_PPM_DISPLAY )
624printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
625__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
626#endif
627}
628*/
629
630/////////////////////////////////////////////////////////////////////////////////////////
631// [3]           Marshaling functions attached to RPC_PROCESS_MAKE_FORK
632/////////////////////////////////////////////////////////////////////////////////////////
633
634///////////////////////////////////////////////////
635void rpc_process_make_fork_client( cxy_t       cxy,
636                                   xptr_t      ref_process_xp,      // in
637                                   xptr_t      parent_thread_xp,    // in
638                                   pid_t     * child_pid,           // out
639                                   thread_t ** child_thread_ptr,    // out     
640                                   error_t   * error )              // out
641{
642#if DEBUG_RPC_PROCESS_MAKE_FORK
643thread_t * this = CURRENT_THREAD;
644uint32_t cycle = (uint32_t)hal_get_cycles();
645if( cycle > DEBUG_RPC_PROCESS_MAKE_FORK )
646printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
647__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
648#endif
649
650    uint32_t responses = 1;
651
652    // initialise RPC descriptor header
653    rpc_desc_t  rpc;
654    rpc.index    = RPC_PROCESS_MAKE_FORK;
655    rpc.blocking = true;
656    rpc.rsp      = &responses;
657
658    // set input arguments in RPC descriptor 
659    rpc.args[0] = (uint64_t)ref_process_xp;
660    rpc.args[1] = (uint64_t)parent_thread_xp;
661
662    // register RPC request in remote RPC fifo
663    rpc_send( cxy , &rpc );
664
665    // get output arguments from RPC descriptor
666    *child_pid         = (pid_t)rpc.args[2];
667    *child_thread_ptr  = (thread_t *)(intptr_t)rpc.args[3];
668    *error             = (error_t)rpc.args[4];     
669
670#if DEBUG_RPC_PROCESS_MAKE_FORK
671cycle = (uint32_t)hal_get_cycles();
672if( cycle > DEBUG_RPC_PROCESS_MAKE_FORK )
673printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
674__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
675#endif
676}
677
678//////////////////////////////////////////////
679void rpc_process_make_fork_server( xptr_t xp )
680{
681#if DEBUG_RPC_PROCESS_MAKE_FORK
682thread_t * this = CURRENT_THREAD;
683uint32_t cycle = (uint32_t)hal_get_cycles();
684if( cycle > DEBUG_RPC_PROCESS_MAKE_FORK )
685printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
686__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
687#endif
688
689    xptr_t     ref_process_xp;     // extended pointer on reference parent process
690    xptr_t     parent_thread_xp;   // extended pointer on parent thread
691    pid_t      child_pid;          // child process identifier
692    thread_t * child_thread_ptr;   // local copy of exec_info structure
693    error_t    error;              // local error status
694
695    // get client cluster identifier and pointer on RPC descriptor
696    cxy_t        client_cxy  = GET_CXY( xp );
697    rpc_desc_t * desc        = GET_PTR( xp );
698
699    // get input arguments from cient RPC descriptor
700    ref_process_xp   = (xptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[0] ) );
701    parent_thread_xp = (xptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[1] ) );
702
703    // call local kernel function
704    error = process_make_fork( ref_process_xp,
705                               parent_thread_xp,
706                               &child_pid,
707                               &child_thread_ptr ); 
708
709    // set output argument into client RPC descriptor
710    hal_remote_s64( XPTR( client_cxy , &desc->args[2] ) , (uint64_t)child_pid );
711    hal_remote_s64( XPTR( client_cxy , &desc->args[3] ) , (uint64_t)(intptr_t)child_thread_ptr );
712    hal_remote_s64( XPTR( client_cxy , &desc->args[4] ) , (uint64_t)error );
713
714#if DEBUG_RPC_PROCESS_MAKE_FORK
715cycle = (uint32_t)hal_get_cycles();
716if( cycle > DEBUG_RPC_PROCESS_MAKE_FORK )
717printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
718__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
719#endif
720}
721
722/////////////////////////////////////////////////////////////////////////////////////////
723// [4]      Marshaling functions attached to RPC_USER_DIR_CREATE 
724/////////////////////////////////////////////////////////////////////////////////////////
725
726////////////////////////////////////////////////////
727void rpc_user_dir_create_client( cxy_t          cxy,
728                                 vfs_inode_t *  inode,
729                                 xptr_t         ref_xp,
730                                 user_dir_t  ** dir )
731{
732#if DEBUG_RPC_USER_DIR_CREATE
733thread_t * this = CURRENT_THREAD;
734uint32_t cycle = (uint32_t)hal_get_cycles();
735if( cycle > DEBUG_RPC_USER_DIR_CREATE)
736printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
737__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
738#endif
739
740    uint32_t responses = 1;
741
742    // initialise RPC descriptor header
743    rpc_desc_t  rpc;
744    rpc.index    = RPC_USER_DIR_CREATE;
745    rpc.blocking = true;
746    rpc.rsp      = &responses;
747
748    // set input arguments in RPC descriptor
749    rpc.args[0] = (uint64_t)(intptr_t)inode;
750    rpc.args[1] = (uint64_t)ref_xp;
751
752    // register RPC request in remote RPC fifo
753    rpc_send( cxy , &rpc );
754
755    // get output argument from RPC descriptor
756    *dir = (user_dir_t *)(intptr_t)rpc.args[2];
757
758#if DEBUG_RPC_USER_DIR_CREATE
759cycle = (uint32_t)hal_get_cycles();
760if( cycle > DEBUG_RPC_USER_DIR_CREATE)
761printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
762__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
763#endif
764}
765
766////////////////////////////////////////////
767void rpc_user_dir_create_server( xptr_t xp )
768{
769#if DEBUG_RPC_USER_DIR_CREATE
770thread_t * this = CURRENT_THREAD;
771uint32_t cycle = (uint32_t)hal_get_cycles();
772if( cycle > DEBUG_RPC_USER_DIR_CREATE)
773printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
774__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
775#endif
776
777    vfs_inode_t * inode;          // pointer on inode in server cluster
778    xptr_t        ref_xp;         // extended pointer on reference user process
779    user_dir_t  * dir;            // pointer on user_dir structure in server cluster
780
781    // get client cluster identifier and pointer on RPC descriptor
782    cxy_t        client_cxy  = GET_CXY( xp );
783    rpc_desc_t * desc        = GET_PTR( xp );
784
785    // get input argument from RPC descriptor
786    inode  = (vfs_inode_t *)(intptr_t)hal_remote_l64(XPTR(client_cxy , &desc->args[0]));
787    ref_xp = (xptr_t)                 hal_remote_l64(XPTR(client_cxy , &desc->args[1]));
788
789    // call kernel function
790    dir = user_dir_create( inode , ref_xp );
791
792    // set output argument into RPC descriptor
793    hal_remote_s64( XPTR( client_cxy , &desc->args[2] ) , (intptr_t)dir );
794
795#if DEBUG_RPC_USER_DIR_CREATE
796cycle = (uint32_t)hal_get_cycles();
797if( cycle > DEBUG_RPC_USER_DIR_CREATE)
798printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
799__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
800#endif
801}
802
803/////////////////////////////////////////////////////////////////////////////////////////
804// [5]      Marshaling functions attached to RPC_USER_DIR_DESTROY
805/////////////////////////////////////////////////////////////////////////////////////////
806
807////////////////////////////////////////////////////
808void rpc_user_dir_destroy_client( cxy_t         cxy,
809                                  user_dir_t  * dir,
810                                  xptr_t        ref_xp )
811{
812#if DEBUG_RPC_USER_DIR_DESTROY
813thread_t * this = CURRENT_THREAD;
814uint32_t cycle = (uint32_t)hal_get_cycles();
815if( cycle > DEBUG_RPC_USER_DIR_DESTROY)
816printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
817__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
818#endif
819
820    uint32_t responses = 1;
821
822    // initialise RPC descriptor header
823    rpc_desc_t  rpc;
824    rpc.index    = RPC_USER_DIR_DESTROY;
825    rpc.blocking = true;
826    rpc.rsp      = &responses;
827
828    // set input arguments in RPC descriptor
829    rpc.args[0] = (uint64_t)(intptr_t)dir;
830    rpc.args[1] = (uint64_t)ref_xp;
831
832    // register RPC request in remote RPC fifo
833    rpc_send( cxy , &rpc );
834
835#if DEBUG_RPC_USER_DIR_DESTROY
836cycle = (uint32_t)hal_get_cycles();
837if( cycle > DEBUG_RPC_USER_DIR_DESTROY)
838printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
839__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
840#endif
841}
842
843/////////////////////////////////////////////
844void rpc_user_dir_destroy_server( xptr_t xp )
845{
846#if DEBUG_RPC_USER_DIR_DESTROY
847thread_t * this = CURRENT_THREAD;
848uint32_t cycle = (uint32_t)hal_get_cycles();
849if( cycle > DEBUG_RPC_USER_DIR_DESTROY)
850printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
851__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
852#endif
853
854    user_dir_t * dir;            // pointer on user_dir structure in server cluster
855    xptr_t       ref_xp;         // extended pointer on reference process
856
857    // get client cluster identifier and pointer on RPC descriptor
858    cxy_t        client_cxy  = GET_CXY( xp );
859    rpc_desc_t * desc        = GET_PTR( xp );
860
861    // get input argument from RPC descriptor
862    dir    = (user_dir_t *)(intptr_t)hal_remote_l64(XPTR(client_cxy , &desc->args[0]));
863    ref_xp = (xptr_t)                hal_remote_l64(XPTR(client_cxy , &desc->args[1]));
864
865    // call kernel function
866    user_dir_destroy( dir , ref_xp );
867
868#if DEBUG_RPC_USER_DIR_DESTROY
869cycle = (uint32_t)hal_get_cycles();
870if( cycle > DEBUG_RPC_USER_DIR_DESTROY)
871printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
872__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
873#endif
874}
875
876/////////////////////////////////////////////////////////////////////////////////////////
877// [6]      Marshaling functions attached to RPC_THREAD_USER_CREATE   
878/////////////////////////////////////////////////////////////////////////////////////////
879
880/////////////////////////////////////////////////////////
881void rpc_thread_user_create_client( cxy_t            cxy, 
882                                    pid_t            pid,         // in
883                                    void           * start_func,  // in
884                                    void           * start_arg,   // in
885                                    pthread_attr_t * attr,        // in
886                                    xptr_t         * thread_xp,   // out
887                                    error_t        * error )      // out
888{
889#if DEBUG_RPC_THREAD_USER_CREATE
890thread_t * this = CURRENT_THREAD;
891uint32_t cycle = (uint32_t)hal_get_cycles();
892if( cycle > DEBUG_RPC_THREAD_USER_CREATE)
893printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
894__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
895#endif
896   
897    uint32_t responses = 1;
898
899    // initialise RPC descriptor header
900    rpc_desc_t  rpc;
901    rpc.index    = RPC_THREAD_USER_CREATE;
902    rpc.blocking = true;
903    rpc.rsp      = &responses;
904
905    // set input arguments in RPC descriptor
906    rpc.args[0] = (uint64_t)pid;
907    rpc.args[1] = (uint64_t)(intptr_t)start_func;
908    rpc.args[2] = (uint64_t)(intptr_t)start_arg;
909    rpc.args[3] = (uint64_t)(intptr_t)attr;
910
911    // register RPC request in remote RPC fifo
912    rpc_send( cxy , &rpc );
913
914    // get output arguments from RPC descriptor
915    *thread_xp = (xptr_t)rpc.args[4];
916    *error     = (error_t)rpc.args[5];
917
918#if DEBUG_RPC_THREAD_USER_CREATE
919cycle = (uint32_t)hal_get_cycles();
920if( cycle > DEBUG_RPC_THREAD_USER_CREATE)
921printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
922__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
923#endif
924}
925
926///////////////////////////////////////////////
927void rpc_thread_user_create_server( xptr_t xp )
928{
929#if DEBUG_RPC_THREAD_USER_CREATE
930thread_t * this = CURRENT_THREAD;
931uint32_t cycle = (uint32_t)hal_get_cycles();
932if( cycle > DEBUG_RPC_THREAD_USER_CREATE)
933printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
934__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
935#endif
936
937    pthread_attr_t * attr_ptr;   // pointer on attributes structure in client cluster
938    pthread_attr_t   attr_copy;  // attributes structure  copy in server cluster
939    thread_t       * thread_ptr; // local pointer on thread descriptor
940    xptr_t           thread_xp;  // extended pointer on thread descriptor
941
942    pid_t            pid;        // process identifier
943    void           * start_func;
944    void           * start_arg;
945    error_t          error;
946
947    // get client cluster identifier and pointer on RPC descriptor
948    cxy_t        client_cxy  = GET_CXY( xp );
949    rpc_desc_t * desc        = GET_PTR( xp );
950
951    // get input arguments from RPC descriptor
952    pid        = (pid_t)                     hal_remote_l64(XPTR(client_cxy , &desc->args[0]));
953    start_func = (void *)(intptr_t)          hal_remote_l64(XPTR(client_cxy , &desc->args[1]));
954    start_arg  = (void *)(intptr_t)          hal_remote_l64(XPTR(client_cxy , &desc->args[2]));
955    attr_ptr   = (pthread_attr_t *)(intptr_t)hal_remote_l64(XPTR(client_cxy , &desc->args[3]));
956
957    // makes a local copy of attributes structure
958    hal_remote_memcpy( XPTR( local_cxy , &attr_copy ),
959                       XPTR( client_cxy , attr_ptr ), 
960                       sizeof(pthread_attr_t) );
961   
962    // call kernel function
963    error = thread_user_create( pid,
964                                start_func,
965                                start_arg,
966                                &attr_copy,
967                                &thread_ptr );
968    // set output arguments
969    thread_xp = XPTR( local_cxy , thread_ptr );
970    hal_remote_s64( XPTR( client_cxy , &desc->args[4] ) , (uint64_t)thread_xp );
971    hal_remote_s64( XPTR( client_cxy , &desc->args[5] ) , (uint64_t)error );
972
973#if DEBUG_RPC_THREAD_USER_CREATE
974cycle = (uint32_t)hal_get_cycles();
975if( cycle > DEBUG_RPC_THREAD_USER_CREATE)
976printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
977__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
978#endif
979}
980
981/////////////////////////////////////////////////////////////////////////////////////////
982// [7]      Marshaling functions attached to RPC_THREAD_KERNEL_CREATE
983/////////////////////////////////////////////////////////////////////////////////////////
984
985////////////////////////////////////////////////////
986void rpc_thread_kernel_create_client( cxy_t     cxy,
987                                      uint32_t  type,        // in
988                                      void    * func,        // in
989                                      void    * args,        // in
990                                      xptr_t  * thread_xp,   // out
991                                      error_t * error )      // out
992{
993#if DEBUG_RPC_THREAD_KERNEL_CREATE
994thread_t * this = CURRENT_THREAD;
995uint32_t cycle = (uint32_t)hal_get_cycles();
996if( cycle > DEBUG_RPC_THREAD_KERNEL_CREATE)
997printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
998__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
999#endif
1000
1001    uint32_t responses = 1;
1002
1003    // initialise RPC descriptor header
1004    rpc_desc_t  rpc;
1005    rpc.index    = RPC_THREAD_KERNEL_CREATE;
1006    rpc.blocking = true;
1007    rpc.rsp      = &responses;
1008
1009    // set input arguments in RPC descriptor
1010    rpc.args[0] = (uint64_t)type;
1011    rpc.args[1] = (uint64_t)(intptr_t)func;
1012    rpc.args[2] = (uint64_t)(intptr_t)args;
1013   
1014    // register RPC request in remote RPC fifo
1015    rpc_send( cxy , &rpc );
1016
1017    // get output arguments from RPC descriptor
1018    *thread_xp = (xptr_t)rpc.args[3];
1019    *error     = (error_t)rpc.args[4];
1020
1021#if DEBUG_RPC_THREAD_KERNEL_CREATE
1022cycle = (uint32_t)hal_get_cycles();
1023if( cycle > DEBUG_RPC_THREAD_KERNEL_CREATE)
1024printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1025__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1026#endif
1027}
1028
1029/////////////////////////////////////////////////
1030void rpc_thread_kernel_create_server( xptr_t xp )
1031{
1032#if DEBUG_RPC_THREAD_KERNEL_CREATE
1033thread_t * this = CURRENT_THREAD;
1034uint32_t cycle = (uint32_t)hal_get_cycles();
1035if( cycle > DEBUG_RPC_THREAD_KERNEL_CREATE)
1036printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1037__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1038#endif
1039
1040    thread_t       * thread_ptr;  // local pointer on thread descriptor
1041    xptr_t           thread_xp;   // extended pointer on thread descriptor
1042    lid_t            core_lid;    // core local index
1043    error_t          error;   
1044
1045    // get client cluster identifier and pointer on RPC descriptor
1046    cxy_t        client_cxy  = GET_CXY( xp );
1047    rpc_desc_t * desc        = GET_PTR( xp );
1048
1049    // get attributes from RPC descriptor
1050    uint32_t  type = (uint32_t)       hal_remote_l64( XPTR( client_cxy , &desc->args[0] ) );
1051    void    * func = (void*)(intptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[1] ) );
1052    void    * args = (void*)(intptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[2] ) );
1053
1054    // select one core
1055    core_lid = cluster_select_local_core( local_cxy );
1056
1057    // call local kernel function
1058    error = thread_kernel_create( &thread_ptr , type , func , args , core_lid );
1059
1060    // set output arguments
1061    thread_xp = XPTR( local_cxy , thread_ptr );
1062    hal_remote_s64( XPTR( client_cxy , &desc->args[1] ) , (uint64_t)error );
1063    hal_remote_s64( XPTR( client_cxy , &desc->args[2] ) , (uint64_t)thread_xp );
1064
1065#if DEBUG_RPC_THREAD_KERNEL_CREATE
1066cycle = (uint32_t)hal_get_cycles();
1067if( cycle > DEBUG_RPC_THREAD_KERNEL_CREATE)
1068printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1069__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1070#endif
1071}
1072
1073/////////////////////////////////////////////////////////////////////////////////////////
1074// [8]   Marshaling functions attached to RPC_VFS_FS_UPDATE_DENTRY
1075/////////////////////////////////////////////////////////////////////////////////////////
1076
1077/////////////////////////////////////////////////////////
1078void rpc_vfs_fs_update_dentry_client( cxy_t          cxy,
1079                                      vfs_inode_t  * inode,
1080                                      vfs_dentry_t * dentry,
1081                                      uint32_t       size,
1082                                      error_t      * error )
1083{
1084#if DEBUG_RPC_VFS_FS_UPDATE_DENTRY
1085thread_t * this = CURRENT_THREAD;
1086uint32_t cycle = (uint32_t)hal_get_cycles();
1087if( cycle > DEBUG_RPC_VFS_FS_UPDATE_DENTRY )
1088printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1089__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1090#endif
1091
1092    uint32_t responses = 1;
1093
1094    // initialise RPC descriptor header
1095    rpc_desc_t  rpc;
1096    rpc.index    = RPC_VFS_FS_UPDATE_DENTRY;
1097    rpc.blocking = true;
1098    rpc.rsp      = &responses;
1099
1100    // set input arguments in RPC descriptor
1101    rpc.args[0] = (uint64_t)(intptr_t)inode;
1102    rpc.args[1] = (uint64_t)(intptr_t)dentry;
1103    rpc.args[2] = (uint64_t)size;
1104
1105    // register RPC request in remote RPC fifo
1106    rpc_send( cxy , &rpc );
1107
1108    // get output values from RPC descriptor
1109    *error   = (error_t)rpc.args[3];
1110
1111#if DEBUG_RPC_VFS_FS_UPDATE_DENTRY
1112cycle = (uint32_t)hal_get_cycles();
1113if( cycle > DEBUG_RPC_VFS_FS_UPDATE_DENTRY )
1114printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1115__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1116#endif
1117}
1118
1119/////////////////////////////////////////////////
1120void rpc_vfs_fs_update_dentry_server( xptr_t xp )
1121{
1122#if DEBUG_RPC_VFS_FS_UPDATE_DENTRY
1123thread_t * this = CURRENT_THREAD;
1124uint32_t cycle = (uint32_t)hal_get_cycles();
1125if( cycle > DEBUG_RPC_VFS_FS_UPDATE_DENTRY )
1126printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1127__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1128#endif
1129
1130    error_t        error;
1131    vfs_inode_t  * inode;
1132    vfs_dentry_t * dentry;
1133    uint32_t       size;
1134
1135    // get client cluster identifier and pointer on RPC descriptor
1136    cxy_t        client_cxy  = GET_CXY( xp );
1137    rpc_desc_t * desc        = GET_PTR( xp );
1138
1139    // get input arguments
1140    inode  = (vfs_inode_t*)(intptr_t) hal_remote_l64(XPTR(client_cxy , &desc->args[0]));
1141    dentry = (vfs_dentry_t*)(intptr_t)hal_remote_l64(XPTR(client_cxy , &desc->args[1]));
1142    size   = (uint32_t)               hal_remote_l64(XPTR(client_cxy , &desc->args[2]));
1143
1144    // call the kernel function
1145    error = vfs_fs_update_dentry( inode , dentry , size );
1146
1147    // set output argument
1148    hal_remote_s64( XPTR( client_cxy , &desc->args[3] ) , (uint64_t)error );
1149
1150#if DEBUG_RPC_VFS_FS_UPDATE_DENTRY
1151cycle = (uint32_t)hal_get_cycles();
1152if( cycle > DEBUG_RPC_VFS_FS_UPDATE_DENTRY )
1153printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1154__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1155#endif
1156}
1157
1158/////////////////////////////////////////////////////////////////////////////////////////
1159// [9]   Marshaling functions attached to RPC_PROCESS_SIGACTION
1160/////////////////////////////////////////////////////////////////////////////////////////
1161
1162////////////////////////////////////////////////////
1163void rpc_process_sigaction_client( cxy_t        cxy,
1164                                   pid_t        pid,
1165                                   uint32_t     action )
1166{
1167#if DEBUG_RPC_PROCESS_SIGACTION
1168uint32_t  cycle = (uint32_t)hal_get_cycles();
1169thread_t * this = CURRENT_THREAD;
1170if( DEBUG_RPC_PROCESS_SIGACTION < cycle )
1171printk("\n[%s] thread[%x,%x] on core %d : enter to %s process %x / cycle %d\n",
1172__FUNCTION__, this->process->pid, this->trdid, this->core->lid,
1173process_action_str( action ), pid, cycle );
1174#endif
1175
1176    uint32_t    responses = 1;
1177    rpc_desc_t  rpc;
1178
1179    // initialise RPC descriptor header
1180    rpc.index    = RPC_PROCESS_SIGACTION;
1181    rpc.blocking = true;
1182    rpc.rsp      = &responses;
1183
1184    // set input arguments in RPC descriptor
1185    rpc.args[0] = (uint64_t)pid;
1186    rpc.args[1] = (uint64_t)action;
1187
1188    // register RPC request in remote RPC fifo
1189    rpc_send( cxy , &rpc );
1190
1191#if DEBUG_RPC_PROCESS_SIGACTION
1192cycle = (uint32_t)hal_get_cycles();
1193if( DEBUG_RPC_PROCESS_SIGACTION < cycle )
1194printk("\n[%s] thread[%x,%x] on core %d : exit after %s process %x / cycle %d\n",
1195__FUNCTION__, this->process->pid, this->trdid, this->core->lid,
1196process_action_str( action ), pid, cycle );
1197#endif
1198}  // end rpc_process_sigaction_client()
1199
1200//////////////////////////////////////////////
1201void rpc_process_sigaction_server( xptr_t xp )
1202{
1203    // get client cluster identifier and pointer on RPC descriptor
1204    cxy_t        client_cxy = GET_CXY( xp );
1205    rpc_desc_t * desc       = GET_PTR( xp );
1206
1207    // get arguments from RPC descriptor
1208    pid_t    pid    = (pid_t)   hal_remote_l64( XPTR(client_cxy , &desc->args[0]) );
1209    uint32_t action = (uint32_t)hal_remote_l64( XPTR(client_cxy , &desc->args[1]) );
1210
1211#if DEBUG_RPC_PROCESS_SIGACTION
1212uint32_t cycle = (uint32_t)hal_get_cycles();
1213thread_t * this = CURRENT_THREAD;
1214if( DEBUG_RPC_PROCESS_SIGACTION < cycle )
1215printk("\n[%s] thread[%x,%x] on core %d : enter to %s process %x / cycle %d\n",
1216__FUNCTION__, this->process->pid, this->trdid, this->core->lid,
1217process_action_str( action ), pid, cycle );
1218#endif
1219
1220    // get client thread pointers
1221    thread_t * client_ptr = hal_remote_lpt( XPTR( client_cxy , &desc->thread ) );
1222    xptr_t     client_xp  = XPTR( client_cxy , client_ptr );
1223
1224    // get local process descriptor
1225    process_t * process = cluster_get_local_process_from_pid( pid );
1226
1227    // call relevant kernel function if found / does nothing if not found
1228    if( process != NULL )
1229    {
1230        if ( action == DELETE_ALL_THREADS  ) process_delete_threads ( process , client_xp ); 
1231        if ( action == BLOCK_ALL_THREADS   ) process_block_threads  ( process ); 
1232        if ( action == UNBLOCK_ALL_THREADS ) process_unblock_threads( process );
1233    }
1234
1235#if DEBUG_RPC_PROCESS_SIGACTION
1236cycle = (uint32_t)hal_get_cycles();
1237if( DEBUG_RPC_PROCESS_SIGACTION < cycle )
1238printk("\n[%s] thread[%x,%x] on core %d : exit after %s process %x / cycle %d\n",
1239__FUNCTION__, this->process->pid, this->trdid, this->core->lid,
1240process_action_str( action ), pid, cycle );
1241#endif
1242} // end rpc_process_sigaction_server()
1243
1244/////////////////////////////////////////////////////////////////////////////////////////
1245// [10]     Marshaling functions attached to RPC_VFS_INODE_CREATE
1246/////////////////////////////////////////////////////////////////////////////////////////
1247
1248/////////////////////////////////////////////////////
1249void rpc_vfs_inode_create_client( cxy_t          cxy,     
1250                                  uint32_t       fs_type,    // in
1251                                  uint32_t       attr,       // in
1252                                  uint32_t       rights,     // in
1253                                  uint32_t       uid,        // in
1254                                  uint32_t       gid,        // in
1255                                  xptr_t       * inode_xp,   // out
1256                                  error_t      * error )     // out
1257{
1258#if DEBUG_RPC_VFS_INODE_CREATE
1259thread_t * this = CURRENT_THREAD;
1260uint32_t cycle = (uint32_t)hal_get_cycles();
1261if( cycle > DEBUG_RPC_VFS_INODE_CREATE )
1262printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1263__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1264#endif
1265
1266    uint32_t responses = 1;
1267
1268    // initialise RPC descriptor header
1269    rpc_desc_t  rpc;
1270    rpc.index    = RPC_VFS_INODE_CREATE;
1271    rpc.blocking = true;
1272    rpc.rsp      = &responses;
1273
1274    // set input arguments in RPC descriptor
1275    rpc.args[0] = (uint64_t)fs_type;
1276    rpc.args[1] = (uint64_t)attr;
1277    rpc.args[2] = (uint64_t)rights;
1278    rpc.args[3] = (uint64_t)uid;
1279    rpc.args[4] = (uint64_t)gid;
1280
1281    // register RPC request in remote RPC fifo
1282    rpc_send( cxy , &rpc );
1283
1284    // get output values from RPC descriptor
1285    *inode_xp = (xptr_t)rpc.args[5];
1286    *error    = (error_t)rpc.args[6];
1287
1288#if DEBUG_RPC_VFS_INODE_CREATE
1289cycle = (uint32_t)hal_get_cycles();
1290if( cycle > DEBUG_RPC_VFS_INODE_CREATE )
1291printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1292__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1293#endif
1294}
1295
1296/////////////////////////////////////////////
1297void rpc_vfs_inode_create_server( xptr_t xp )
1298{
1299#if DEBUG_RPC_VFS_INODE_CREATE
1300thread_t * this = CURRENT_THREAD;
1301uint32_t cycle = (uint32_t)hal_get_cycles();
1302if( cycle > DEBUG_RPC_VFS_INODE_CREATE )
1303printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1304__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1305#endif
1306
1307    uint32_t         fs_type;
1308    uint32_t         attr;
1309    uint32_t         rights;
1310    uint32_t         uid;
1311    uint32_t         gid;
1312    xptr_t           inode_xp;
1313    error_t          error;
1314
1315    // get client cluster identifier and pointer on RPC descriptor
1316    cxy_t        client_cxy  = GET_CXY( xp );
1317    rpc_desc_t * desc        = GET_PTR( xp );
1318
1319    // get input arguments from client rpc descriptor
1320    fs_type    = (uint32_t)  hal_remote_l64( XPTR( client_cxy , &desc->args[0] ) );
1321    attr       = (uint32_t)  hal_remote_l64( XPTR( client_cxy , &desc->args[1] ) );
1322    rights     = (uint32_t)  hal_remote_l64( XPTR( client_cxy , &desc->args[2] ) );
1323    uid        = (uid_t)     hal_remote_l64( XPTR( client_cxy , &desc->args[3] ) );
1324    gid        = (gid_t)     hal_remote_l64( XPTR( client_cxy , &desc->args[4] ) );
1325
1326    // call local kernel function
1327    error = vfs_inode_create( fs_type,
1328                              attr,
1329                              rights,
1330                              uid,
1331                              gid,
1332                              &inode_xp );
1333
1334    // set output arguments
1335    hal_remote_s64( XPTR( client_cxy , &desc->args[5] ) , (uint64_t)inode_xp );
1336    hal_remote_s64( XPTR( client_cxy , &desc->args[6] ) , (uint64_t)error );
1337
1338#if DEBUG_RPC_VFS_INODE_CREATE
1339cycle = (uint32_t)hal_get_cycles();
1340if( cycle > DEBUG_RPC_VFS_INODE_CREATE )
1341printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1342__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1343#endif
1344}
1345
1346/////////////////////////////////////////////////////////////////////////////////////////
1347// [11]          Marshaling functions attached to RPC_VFS_INODE_DESTROY
1348/////////////////////////////////////////////////////////////////////////////////////////
1349
1350/////////////////////////////////////////////////////////////
1351void rpc_vfs_inode_destroy_client( cxy_t                cxy,
1352                                   struct vfs_inode_s * inode )
1353{
1354#if DEBUG_RPC_VFS_INODE_DESTROY
1355thread_t * this = CURRENT_THREAD;
1356uint32_t cycle = (uint32_t)hal_get_cycles();
1357if( cycle > DEBUG_RPC_VFS_INODE_DESTROY )
1358printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1359__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1360#endif
1361
1362    uint32_t responses = 1;
1363
1364    // initialise RPC descriptor header
1365    rpc_desc_t  rpc;
1366    rpc.index    = RPC_VFS_INODE_DESTROY;
1367    rpc.blocking = true;
1368    rpc.rsp      = &responses;
1369
1370    // set input arguments in RPC descriptor
1371    rpc.args[0] = (uint64_t)(intptr_t)inode;
1372   
1373    // register RPC request in remote RPC fifo
1374    rpc_send( cxy , &rpc );
1375
1376#if DEBUG_RPC_VFS_INODE_DESTROY
1377cycle = (uint32_t)hal_get_cycles();
1378if( cycle > DEBUG_RPC_VFS_INODE_DESTROY )
1379printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1380__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1381#endif
1382}
1383
1384//////////////////////////////////////////////
1385void rpc_vfs_inode_destroy_server( xptr_t xp )
1386{
1387#if DEBUG_RPC_VFS_INODE_DESTROY
1388thread_t * this = CURRENT_THREAD;
1389uint32_t cycle = (uint32_t)hal_get_cycles();
1390if( cycle > DEBUG_RPC_VFS_INODE_DESTROY )
1391printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1392__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1393#endif
1394
1395    vfs_inode_t * inode;
1396
1397    // get client cluster identifier and pointer on RPC descriptor
1398    cxy_t        client_cxy  = GET_CXY( xp );
1399    rpc_desc_t * desc        = GET_PTR( xp );
1400
1401    // get argument "inode" from client RPC descriptor
1402    inode = (vfs_inode_t *)(intptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[0] ) );
1403                       
1404    // call local kernel function
1405    vfs_inode_destroy( inode );
1406
1407#if DEBUG_RPC_VFS_INODE_DESTROY
1408cycle = (uint32_t)hal_get_cycles();
1409if( cycle > DEBUG_RPC_VFS_INODE_DESTROY )
1410printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1411__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1412#endif
1413}
1414
1415/////////////////////////////////////////////////////////////////////////////////////////
1416// [12]          Marshaling functions attached to RPC_VFS_DENTRY_CREATE
1417/////////////////////////////////////////////////////////////////////////////////////////
1418
1419//////////////////////////////////////////////////////////////
1420void rpc_vfs_dentry_create_client( cxy_t                  cxy,
1421                                   uint32_t               type,         // in
1422                                   char                 * name,         // in
1423                                   xptr_t               * dentry_xp,    // out
1424                                   error_t              * error )       // out
1425{
1426#if DEBUG_RPC_VFS_DENTRY_CREATE
1427thread_t * this = CURRENT_THREAD;
1428uint32_t cycle = (uint32_t)hal_get_cycles();
1429if( cycle > DEBUG_RPC_VFS_DENTRY_CREATE )
1430printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1431__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1432#endif
1433
1434    uint32_t responses = 1;
1435
1436    // initialise RPC descriptor header
1437    rpc_desc_t  rpc;
1438    rpc.index    = RPC_VFS_DENTRY_CREATE;
1439    rpc.blocking = true;
1440    rpc.rsp      = &responses;
1441
1442    // set input arguments in RPC descriptor
1443    rpc.args[0] = (uint64_t)type;
1444    rpc.args[1] = (uint64_t)(intptr_t)name;
1445
1446    // register RPC request in remote RPC fifo
1447    rpc_send( cxy , &rpc );
1448
1449    // get output values from RPC descriptor
1450    *dentry_xp = (xptr_t)rpc.args[2];
1451    *error     = (error_t)rpc.args[3];
1452
1453#if DEBUG_RPC_VFS_DENTRY_CREATE
1454cycle = (uint32_t)hal_get_cycles();
1455if( cycle > DEBUG_RPC_VFS_DENTRY_CREATE )
1456printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1457__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1458#endif
1459}
1460
1461//////////////////////////////////////////////
1462void rpc_vfs_dentry_create_server( xptr_t xp )
1463{
1464#if DEBUG_RPC_VFS_DENTRY_CREATE
1465thread_t * this = CURRENT_THREAD;
1466uint32_t cycle = (uint32_t)hal_get_cycles();
1467if( cycle > DEBUG_RPC_VFS_DENTRY_CREATE )
1468printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1469__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1470#endif
1471
1472    uint32_t      type;
1473    char        * name;
1474    xptr_t        dentry_xp;
1475    error_t       error;
1476    char          name_copy[CONFIG_VFS_MAX_NAME_LENGTH];
1477
1478    // get client cluster identifier and pointer on RPC descriptor
1479    cxy_t        client_cxy  = GET_CXY( xp );
1480    rpc_desc_t * desc        = GET_PTR( xp );
1481
1482    // get arguments "name", "type", and "parent" from client RPC descriptor
1483    type   = (uint32_t)         hal_remote_l64( XPTR( client_cxy , &desc->args[0] ) );
1484    name   = (char *)(intptr_t) hal_remote_l64( XPTR( client_cxy , &desc->args[1] ) );
1485
1486    // makes a local copy of  name
1487    hal_remote_strcpy( XPTR( local_cxy , name_copy ),
1488                       XPTR( client_cxy , name ) );
1489
1490    // call local kernel function
1491    error = vfs_dentry_create( type,
1492                               name_copy,
1493                               &dentry_xp );
1494    // set output arguments
1495    hal_remote_s64( XPTR( client_cxy , &desc->args[2] ) , (uint64_t)dentry_xp );
1496    hal_remote_s64( XPTR( client_cxy , &desc->args[3] ) , (uint64_t)error );
1497
1498#if DEBUG_RPC_VFS_DENTRY_CREATE
1499cycle = (uint32_t)hal_get_cycles();
1500if( cycle > DEBUG_RPC_VFS_DENTRY_CREATE )
1501printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1502__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1503#endif
1504}
1505
1506/////////////////////////////////////////////////////////////////////////////////////////
1507// [13]          Marshaling functions attached to RPC_VFS_DENTRY_DESTROY
1508/////////////////////////////////////////////////////////////////////////////////////////
1509
1510///////////////////////////////////////////////////////
1511void rpc_vfs_dentry_destroy_client( cxy_t          cxy,
1512                                    vfs_dentry_t * dentry )
1513{
1514#if DEBUG_RPC_VFS_DENTRY_DESTROY
1515thread_t * this = CURRENT_THREAD;
1516uint32_t cycle = (uint32_t)hal_get_cycles();
1517if( cycle > DEBUG_RPC_VFS_DENTRY_DESTROY )
1518printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1519__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1520#endif
1521
1522    uint32_t responses = 1;
1523
1524    // initialise RPC descriptor header
1525    rpc_desc_t  rpc;
1526    rpc.index    = RPC_VFS_DENTRY_DESTROY;
1527    rpc.blocking = true;
1528    rpc.rsp      = &responses;
1529
1530    // set input arguments in RPC descriptor
1531    rpc.args[0] = (uint64_t)(intptr_t)dentry;
1532   
1533    // register RPC request in remote RPC fifo
1534    rpc_send( cxy , &rpc );
1535
1536#if DEBUG_RPC_VFS_DENTRY_DESTROY
1537cycle = (uint32_t)hal_get_cycles();
1538if( cycle > DEBUG_RPC_VFS_DENTRY_DESTROY )
1539printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1540__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1541#endif
1542}
1543
1544///////////////////////////////////////////////
1545void rpc_vfs_dentry_destroy_server( xptr_t xp )
1546{
1547#if DEBUG_RPC_VFS_DENTRY_DESTROY
1548thread_t * this = CURRENT_THREAD;
1549uint32_t cycle = (uint32_t)hal_get_cycles();
1550if( cycle > DEBUG_RPC_VFS_DENTRY_DESTROY )
1551printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1552__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1553#endif
1554
1555    vfs_dentry_t * dentry;
1556
1557    // get client cluster identifier and pointer on RPC descriptor
1558    cxy_t        client_cxy  = GET_CXY( xp );
1559    rpc_desc_t * desc        = GET_PTR( xp );
1560
1561    // get arguments "dentry" from client RPC descriptor
1562    dentry = (vfs_dentry_t *)(intptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[0] ) );
1563                       
1564    // call local kernel function
1565    vfs_dentry_destroy( dentry );
1566
1567#if DEBUG_RPC_VFS_DENTRY_DESTROY
1568cycle = (uint32_t)hal_get_cycles();
1569if( cycle > DEBUG_RPC_VFS_DENTRY_DESTROY )
1570printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1571__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1572#endif
1573}
1574
1575
1576/////////////////////////////////////////////////////////////////////////////////////////
1577// [14]          Marshaling functions attached to RPC_VFS_FILE_CREATE 
1578/////////////////////////////////////////////////////////////////////////////////////////
1579
1580//////////////////////////////////////////////////////////////
1581void rpc_vfs_file_create_client( cxy_t                  cxy,
1582                                 struct vfs_inode_s   * inode,       // in
1583                                 uint32_t               file_attr,   // in
1584                                 xptr_t               * file_xp,     // out
1585                                 error_t              * error )      // out
1586{
1587#if DEBUG_RPC_VFS_FILE_CREATE
1588thread_t * this = CURRENT_THREAD;
1589uint32_t cycle = (uint32_t)hal_get_cycles();
1590if( cycle > DEBUG_RPC_VFS_FILE_CREATE )
1591printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1592__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1593#endif
1594
1595    uint32_t responses = 1;
1596
1597    // initialise RPC descriptor header
1598    rpc_desc_t  rpc;
1599    rpc.index    = RPC_VFS_FILE_CREATE;
1600    rpc.blocking = true;
1601    rpc.rsp      = &responses;
1602
1603    // set input arguments in RPC descriptor
1604    rpc.args[0] = (uint64_t)(intptr_t)inode;
1605    rpc.args[1] = (uint64_t)file_attr;
1606
1607    // register RPC request in remote RPC fifo
1608    rpc_send( cxy , &rpc );
1609
1610    // get output values from RPC descriptor
1611    *file_xp = (xptr_t)rpc.args[2];
1612    *error   = (error_t)rpc.args[3];
1613
1614#if DEBUG_RPC_VFS_FILE_CREATE
1615cycle = (uint32_t)hal_get_cycles();
1616if( cycle > DEBUG_RPC_VFS_FILE_CREATE )
1617printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1618__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1619#endif
1620}
1621
1622////////////////////////////////////////////
1623void rpc_vfs_file_create_server( xptr_t xp )
1624{
1625#if DEBUG_RPC_VFS_FILE_CREATE
1626thread_t * this = CURRENT_THREAD;
1627uint32_t cycle = (uint32_t)hal_get_cycles();
1628if( cycle > DEBUG_RPC_VFS_FILE_CREATE )
1629printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1630__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1631#endif
1632
1633    uint32_t      file_attr;
1634    vfs_inode_t * inode;
1635    xptr_t        file_xp;
1636    error_t       error;
1637
1638    // get client cluster identifier and pointer on RPC descriptor
1639    cxy_t        client_cxy  = GET_CXY( xp );
1640    rpc_desc_t * desc        = GET_PTR( xp );
1641
1642    // get arguments "file_attr" and "inode" from client RPC descriptor
1643    inode     = (vfs_inode_t *)(intptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[0] ) );
1644    file_attr = (uint32_t)               hal_remote_l64( XPTR( client_cxy , &desc->args[1] ) );
1645                       
1646    // call local kernel function
1647    error = vfs_file_create( inode,
1648                             file_attr,
1649                             &file_xp );
1650 
1651    // set output arguments
1652    hal_remote_s64( XPTR( client_cxy , &desc->args[2] ) , (uint64_t)file_xp );
1653    hal_remote_s64( XPTR( client_cxy , &desc->args[3] ) , (uint64_t)error );
1654
1655#if DEBUG_RPC_VFS_FILE_CREATE
1656cycle = (uint32_t)hal_get_cycles();
1657if( cycle > DEBUG_RPC_VFS_FILE_CREATE )
1658printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1659__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1660#endif
1661}
1662
1663/////////////////////////////////////////////////////////////////////////////////////////
1664// [15]          Marshaling functions attached to RPC_VFS_FILE_DESTROY 
1665/////////////////////////////////////////////////////////////////////////////////////////
1666
1667///////////////////////////////////////////////////
1668void rpc_vfs_file_destroy_client( cxy_t        cxy,
1669                                  vfs_file_t * file )
1670{
1671#if DEBUG_RPC_VFS_FILE_DESTROY
1672thread_t * this = CURRENT_THREAD;
1673uint32_t cycle = (uint32_t)hal_get_cycles();
1674if( cycle > DEBUG_RPC_VFS_FILE_DESTROY )
1675printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1676__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1677#endif
1678
1679    uint32_t responses = 1;
1680
1681    // initialise RPC descriptor header
1682    rpc_desc_t  rpc;
1683    rpc.index    = RPC_VFS_FILE_DESTROY;
1684    rpc.blocking = true;
1685    rpc.rsp      = &responses;
1686
1687    // set input arguments in RPC descriptor
1688    rpc.args[0] = (uint64_t)(intptr_t)file;
1689   
1690    // register RPC request in remote RPC fifo
1691    rpc_send( cxy , &rpc );
1692
1693#if DEBUG_RPC_VFS_FILE_DESTROY
1694cycle = (uint32_t)hal_get_cycles();
1695if( cycle > DEBUG_RPC_VFS_FILE_DESTROY )
1696printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1697__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1698#endif
1699}
1700
1701/////////////////////////////////////////////
1702void rpc_vfs_file_destroy_server( xptr_t xp )
1703{
1704#if DEBUG_RPC_VFS_FILE_DESTROY
1705thread_t * this = CURRENT_THREAD;
1706uint32_t cycle = (uint32_t)hal_get_cycles();
1707if( cycle > DEBUG_RPC_VFS_FILE_DESTROY )
1708printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1709__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1710#endif
1711
1712    vfs_file_t * file;
1713
1714    // get client cluster identifier and pointer on RPC descriptor
1715    cxy_t        client_cxy  = GET_CXY( xp );
1716    rpc_desc_t * desc        = GET_PTR( xp );
1717
1718    // get arguments "dentry" from client RPC descriptor
1719    file = (vfs_file_t *)(intptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[0] ) );
1720                       
1721    // call local kernel function
1722    vfs_file_destroy( file );
1723
1724#if DEBUG_RPC_VFS_FILE_DESTROY
1725cycle = (uint32_t)hal_get_cycles();
1726if( cycle > DEBUG_RPC_VFS_FILE_DESTROY )
1727printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1728__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
1729#endif
1730}
1731
1732/////////////////////////////////////////////////////////////////////////////////////////
1733// [16]      Marshaling functions attached to RPC_VFS_FS_GET_DENTRY
1734/////////////////////////////////////////////////////////////////////////////////////////
1735
1736/////////////////////////////////////////////////////////
1737void rpc_vfs_fs_new_dentry_client( cxy_t         cxy,
1738                                   vfs_inode_t * parent_inode,    // in
1739                                   char        * name,            // in
1740                                   xptr_t        child_inode_xp,  // in
1741                                   error_t     * error )          // out
1742{
1743#if DEBUG_RPC_VFS_FS_NEW_DENTRY
1744thread_t * this = CURRENT_THREAD;
1745uint32_t cycle = (uint32_t)hal_get_cycles();
1746if( cycle > DEBUG_RPC_VFS_FS_NEW_DENTRY )
1747printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1748__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1749#endif
1750
1751    uint32_t responses = 1;
1752
1753    // initialise RPC descriptor header
1754    rpc_desc_t  rpc;
1755    rpc.index    = RPC_VFS_FS_NEW_DENTRY;
1756    rpc.blocking = true;
1757    rpc.rsp      = &responses;
1758
1759    // set input arguments in RPC descriptor
1760    rpc.args[0] = (uint64_t)(intptr_t)parent_inode;
1761    rpc.args[1] = (uint64_t)(intptr_t)name;
1762    rpc.args[2] = (uint64_t)child_inode_xp;
1763
1764    // register RPC request in remote RPC fifo
1765    rpc_send( cxy , &rpc );
1766
1767    // get output values from RPC descriptor
1768    *error   = (error_t)rpc.args[3];
1769
1770#if DEBUG_RPC_VFS_FS_NEW_DENTRY
1771cycle = (uint32_t)hal_get_cycles();
1772if( cycle > DEBUG_RPC_VFS_FS_NEW_DENTRY )
1773printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1774__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1775#endif
1776}
1777
1778//////////////////////////////////////////////
1779void rpc_vfs_fs_new_dentry_server( xptr_t xp )
1780{
1781#if DEBUG_RPC_VFS_FS_NEW_DENTRY
1782thread_t * this = CURRENT_THREAD;
1783uint32_t cycle = (uint32_t)hal_get_cycles();
1784if( cycle > DEBUG_RPC_VFS_FS_NEW_DENTRY )
1785printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1786__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1787#endif
1788
1789    error_t       error;
1790    vfs_inode_t * parent;
1791    xptr_t        child_xp;
1792    char        * name;
1793
1794    char          name_copy[CONFIG_VFS_MAX_NAME_LENGTH];
1795
1796    // get client cluster identifier and pointer on RPC descriptor
1797    cxy_t        client_cxy  = GET_CXY( xp );
1798    rpc_desc_t * desc        = GET_PTR( xp );
1799
1800    // get arguments "parent", "name", and "child_xp"
1801    parent     = (vfs_inode_t*)(intptr_t)hal_remote_l64(XPTR(client_cxy , &desc->args[0]));
1802    name       = (char*)(intptr_t)       hal_remote_l64(XPTR(client_cxy , &desc->args[1]));
1803    child_xp   = (xptr_t)                hal_remote_l64(XPTR(client_cxy , &desc->args[2]));
1804
1805    // get name local copy
1806    hal_remote_strcpy( XPTR( local_cxy , name_copy ) ,
1807                       XPTR( client_cxy , name ) );
1808
1809    // call the kernel function
1810    error = vfs_fs_new_dentry( parent , name_copy , child_xp );
1811
1812    // set output argument
1813    hal_remote_s64( XPTR( client_cxy , &desc->args[3] ) , (uint64_t)error );
1814
1815#if DEBUG_RPC_VFS_FS_NEW_DENTRY
1816cycle = (uint32_t)hal_get_cycles();
1817if( cycle > DEBUG_RPC_VFS_FS_NEW_DENTRY )
1818printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1819__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1820#endif
1821}
1822
1823/////////////////////////////////////////////////////////////////////////////////////////
1824// [17]      Marshaling function attached to RPC_VFS_FS_ADD_DENTRY 
1825/////////////////////////////////////////////////////////////////////////////////////////
1826
1827void rpc_vfs_fs_add_dentry_client( cxy_t          cxy,
1828                                   vfs_inode_t  * parent,     // in
1829                                   vfs_dentry_t * dentry,     // in
1830                                   error_t      * error )     // out
1831{
1832#if DEBUG_RPC_VFS_FS_ADD_DENTRY
1833thread_t * this = CURRENT_THREAD;
1834uint32_t cycle = (uint32_t)hal_get_cycles();
1835if( cycle > DEBUG_RPC_VFS_FS_ADD_DENTRY )
1836printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1837__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1838#endif
1839
1840    uint32_t responses = 1;
1841
1842    // initialise RPC descriptor header
1843    rpc_desc_t  rpc;
1844    rpc.index    = RPC_VFS_FS_ADD_DENTRY;
1845    rpc.blocking = true;
1846    rpc.rsp      = &responses;
1847
1848    // set input arguments in RPC descriptor
1849    rpc.args[0] = (uint64_t)(intptr_t)parent;
1850    rpc.args[1] = (uint64_t)(intptr_t)dentry;
1851
1852    // register RPC request in remote RPC fifo
1853    rpc_send( cxy , &rpc );
1854
1855    // get output values from RPC descriptor
1856    *error   = (error_t)rpc.args[2];
1857
1858#if DEBUG_RPC_VFS_FS_ADD_DENTRY
1859cycle = (uint32_t)hal_get_cycles();
1860if( cycle > DEBUG_RPC_VFS_FS_ADD_DENTRY )
1861printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1862__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1863#endif
1864}
1865
1866//////////////////////////////////////////////
1867void rpc_vfs_fs_add_dentry_server( xptr_t xp )
1868{
1869#if DEBUG_RPC_VFS_FS_ADD_DENTRY
1870thread_t * this = CURRENT_THREAD;
1871uint32_t cycle = (uint32_t)hal_get_cycles();
1872if( cycle > DEBUG_RPC_VFS_FS_ADD_DENTRY )
1873printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1874__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1875#endif
1876
1877    error_t        error;
1878    vfs_inode_t  * parent;
1879    vfs_dentry_t * dentry;
1880
1881    // get client cluster identifier and pointer on RPC descriptor
1882    cxy_t        client_cxy  = GET_CXY( xp );
1883    rpc_desc_t * desc        = GET_PTR( xp );
1884
1885    // get input arguments
1886    parent = (vfs_inode_t*)(intptr_t) hal_remote_l64(XPTR(client_cxy , &desc->args[0]));
1887    dentry = (vfs_dentry_t*)(intptr_t)hal_remote_l64(XPTR(client_cxy , &desc->args[1]));
1888
1889    // call the kernel function
1890    error = vfs_fs_add_dentry( parent , dentry );
1891
1892    // set output argument
1893    hal_remote_s64( XPTR( client_cxy , &desc->args[2] ) , (uint64_t)error );
1894
1895#if DEBUG_RPC_VFS_FS_ADD_DENTRY
1896cycle = (uint32_t)hal_get_cycles();
1897if( cycle > DEBUG_RPC_VFS_FS_ADD_DENTRY )
1898printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1899__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1900#endif
1901}
1902
1903/////////////////////////////////////////////////////////////////////////////////////////
1904// [18]      Marshaling function attached to RPC_VFS_FS_REMOVE_DENTRY
1905/////////////////////////////////////////////////////////////////////////////////////////
1906
1907void rpc_vfs_fs_remove_dentry_client( cxy_t          cxy,
1908                                      vfs_inode_t  * parent,     // in
1909                                      vfs_dentry_t * dentry,     // in
1910                                      error_t      * error )     // out
1911{
1912#if DEBUG_RPC_VFS_FS_REMOVE_DENTRY
1913thread_t * this = CURRENT_THREAD;
1914uint32_t cycle = (uint32_t)hal_get_cycles();
1915if( cycle > DEBUG_RPC_VFS_FS_REMOVE_DENTRY )
1916printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1917__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1918#endif
1919
1920    uint32_t responses = 1;
1921
1922    // initialise RPC descriptor header
1923    rpc_desc_t  rpc;
1924    rpc.index    = RPC_VFS_FS_REMOVE_DENTRY;
1925    rpc.blocking = true;
1926    rpc.rsp      = &responses;
1927
1928    // set input arguments in RPC descriptor
1929    rpc.args[0] = (uint64_t)(intptr_t)parent;
1930    rpc.args[1] = (uint64_t)(intptr_t)dentry;
1931
1932    // register RPC request in remote RPC fifo
1933    rpc_send( cxy , &rpc );
1934
1935    // get output values from RPC descriptor
1936    *error   = (error_t)rpc.args[2];
1937
1938#if DEBUG_RPC_VFS_FS_REMOVE_DENTRY
1939cycle = (uint32_t)hal_get_cycles();
1940if( cycle > DEBUG_RPC_VFS_FS_REMOVE_DENTRY )
1941printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1942__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1943#endif
1944}
1945
1946/////////////////////////////////////////////////
1947void rpc_vfs_fs_remove_dentry_server( xptr_t xp )
1948{
1949#if DEBUG_RPC_VFS_FS_REMOVE_DENTRY
1950thread_t * this = CURRENT_THREAD;
1951uint32_t cycle = (uint32_t)hal_get_cycles();
1952if( cycle > DEBUG_RPC_VFS_FS_REMOVE_DENTRY )
1953printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1954__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1955#endif
1956
1957    error_t        error;
1958    vfs_inode_t  * parent;
1959    vfs_dentry_t * dentry;
1960
1961    // get client cluster identifier and pointer on RPC descriptor
1962    cxy_t        client_cxy  = GET_CXY( xp );
1963    rpc_desc_t * desc        = GET_PTR( xp );
1964
1965    // get input arguments
1966    parent = (vfs_inode_t*)(intptr_t) hal_remote_l64(XPTR(client_cxy , &desc->args[0]));
1967    dentry = (vfs_dentry_t*)(intptr_t)hal_remote_l64(XPTR(client_cxy , &desc->args[1]));
1968
1969    // call the kernel function
1970    error = vfs_fs_remove_dentry( parent , dentry );
1971
1972    // set output argument
1973    hal_remote_s64( XPTR( client_cxy , &desc->args[2] ) , (uint64_t)error );
1974
1975#if DEBUG_RPC_VFS_FS_REMOVE_DENTRY
1976cycle = (uint32_t)hal_get_cycles();
1977if( cycle > DEBUG_RPC_VFS_FS_REMOVE_DENTRY )
1978printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
1979__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1980#endif
1981}
1982
1983/////////////////////////////////////////////////////////////////////////////////////////
1984// [19]     Marshaling functions attached to RPC_VFS_INODE_LOAD_ALL_PAGES
1985/////////////////////////////////////////////////////////////////////////////////////////
1986
1987////////////////////////////////////////////////////////////
1988void rpc_vfs_inode_load_all_pages_client( cxy_t         cxy,
1989                                          vfs_inode_t * inode,      // in
1990                                          error_t     * error )     // out
1991{
1992#if DEBUG_RPC_VFS_INODE_LOAD_ALL_PAGES
1993thread_t * this = CURRENT_THREAD;
1994uint32_t cycle = (uint32_t)hal_get_cycles();
1995if( cycle > DEBUG_RPC_VFS_INODE_LOAD_ALL_PAGES )
1996printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
1997__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
1998#endif
1999
2000    uint32_t responses = 1;
2001
2002    // initialise RPC descriptor header
2003    rpc_desc_t  rpc;
2004    rpc.index    = RPC_VFS_INODE_LOAD_ALL_PAGES;
2005    rpc.blocking = true;
2006    rpc.rsp      = &responses;
2007
2008    // set input arguments in RPC descriptor
2009    rpc.args[0] = (uint64_t)(intptr_t)inode;
2010
2011    // register RPC request in remote RPC fifo
2012    rpc_send( cxy , &rpc );
2013
2014    // get output values from RPC descriptor
2015    *error   = (error_t)rpc.args[1];
2016
2017#if DEBUG_RPC_VFS_INODE_LOAD_ALL_PAGES
2018cycle = (uint32_t)hal_get_cycles();
2019if( cycle > DEBUG_RPC_VFS_INODE_LOAD_ALL_PAGES )
2020printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2021__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2022#endif
2023}
2024
2025/////////////////////////////////////////////////////
2026void rpc_vfs_inode_load_all_pages_server( xptr_t xp )
2027{
2028#if DEBUG_RPC_VFS_INODE_LOAD_ALL_PAGES
2029thread_t * this = CURRENT_THREAD;
2030uint32_t cycle = (uint32_t)hal_get_cycles();
2031if( cycle > DEBUG_RPC_VFS_INODE_LOAD_ALL_PAGES )
2032printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2033__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2034#endif
2035
2036    error_t       error;
2037    vfs_inode_t * inode;
2038
2039    // get client cluster identifier and pointer on RPC descriptor
2040    cxy_t        client_cxy  = GET_CXY( xp );
2041    rpc_desc_t * desc        = GET_PTR( xp );
2042
2043    // get input argument
2044    inode = (vfs_inode_t*)(intptr_t)hal_remote_l64(XPTR(client_cxy , &desc->args[0]));
2045
2046    // call the kernel function
2047    error = vfs_inode_load_all_pages( inode );
2048
2049    // set output argument
2050    hal_remote_s64( XPTR( client_cxy , &desc->args[1] ) , (uint64_t)error );
2051
2052#if DEBUG_RPC_VFS_INODE_LOAD_ALL_PAGES
2053cycle = (uint32_t)hal_get_cycles();
2054if( cycle > DEBUG_RPC_VFS_INODE_LOAD_ALL_PAGES )
2055printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2056__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2057#endif
2058}
2059
2060/////////////////////////////////////////////////////////////////////////////////////////
2061// [20]          RPC_VMM_GET_VSEG deprecated [AG] sept 2019
2062/////////////////////////////////////////////////////////////////////////////////////////
2063
2064/*
2065//////////////////////////////////////////////////
2066void rpc_vmm_get_vseg_client( cxy_t       cxy,     
2067                              process_t * process,     // in 
2068                              intptr_t    vaddr,       // in 
2069                              xptr_t    * vseg_xp,     // out
2070                              error_t   * error )      // out
2071{
2072#if DEBUG_RPC_VMM_GET_VSEG
2073thread_t * this = CURRENT_THREAD;
2074uint32_t cycle = (uint32_t)hal_get_cycles();
2075if( cycle > DEBUG_RPC_VMM_GET_VSEG )
2076printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2077__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2078#endif
2079
2080    uint32_t responses = 1;
2081
2082    // initialise RPC descriptor header
2083    rpc_desc_t  rpc;
2084    rpc.index    = RPC_VMM_GET_VSEG;
2085    rpc.blocking = true;
2086    rpc.rsp      = &responses;
2087
2088    // set input arguments in RPC descriptor
2089    rpc.args[0] = (uint64_t)(intptr_t)process;
2090    rpc.args[1] = (uint64_t)vaddr;
2091
2092    // register RPC request in remote RPC fifo
2093    rpc_send( cxy , &rpc );
2094
2095    // get output argument from rpc descriptor
2096    *vseg_xp = rpc.args[2];
2097    *error   = (error_t)rpc.args[3];
2098
2099#if DEBUG_RPC_VMM_GET_VSEG
2100cycle = (uint32_t)hal_get_cycles();
2101if( cycle > DEBUG_RPC_VMM_GET_VSEG )
2102printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2103__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2104#endif
2105}
2106
2107/////////////////////////////////////////
2108void rpc_vmm_get_vseg_server( xptr_t xp )
2109{
2110#if DEBUG_RPC_VMM_GET_VSEG
2111thread_t * this = CURRENT_THREAD;
2112uint32_t cycle = (uint32_t)hal_get_cycles();
2113if( cycle > DEBUG_RPC_VMM_GET_VSEG )
2114printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2115__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2116#endif
2117
2118    process_t   * process;
2119    intptr_t      vaddr;
2120    vseg_t      * vseg_ptr;
2121    xptr_t        vseg_xp;
2122    error_t       error;
2123
2124    // get client cluster identifier and pointer on RPC descriptor
2125    cxy_t        client_cxy  = GET_CXY( xp );
2126    rpc_desc_t * desc        = GET_PTR( xp );
2127
2128    // get input argument from client RPC descriptor
2129    process = (process_t *)(intptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[0] ) );
2130    vaddr   = (intptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[1] ) );
2131   
2132    // call local kernel function
2133    error = vmm_get_vseg( process , vaddr , &vseg_ptr );
2134
2135    // set output arguments to client RPC descriptor
2136    vseg_xp = XPTR( local_cxy , vseg_ptr );
2137    hal_remote_s64( XPTR( client_cxy , &desc->args[2] ) , (uint64_t)vseg_xp );
2138    hal_remote_s64( XPTR( client_cxy , &desc->args[3] ) , (uint64_t)error );
2139
2140#if DEBUG_RPC_VMM_GET_VSEG
2141cycle = (uint32_t)hal_get_cycles();
2142if( cycle > DEBUG_RPC_VMM_GET_VSEG )
2143printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2144__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2145#endif
2146}
2147*/
2148
2149/////////////////////////////////////////////////////////////////////////////////////////
2150// [21]    undefined
2151/////////////////////////////////////////////////////////////////////////////////////////
2152
2153/////////////////////////////////////////////////////////////////////////////////////////
2154// [22]          RPC_KCM_ALLOC deprecated [AG] sept 2019
2155/////////////////////////////////////////////////////////////////////////////////////////
2156
2157/*
2158//////////////////////////////////////////
2159void rpc_kcm_alloc_client( cxy_t      cxy,
2160                           uint32_t   kmem_type,   // in
2161                           xptr_t   * buf_xp )     // out
2162{
2163#if DEBUG_RPC_KCM_ALLOC
2164thread_t * this = CURRENT_THREAD;
2165uint32_t cycle = (uint32_t)hal_get_cycles();
2166if( cycle > DEBUG_RPC_KCM_ALLOC )
2167printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2168__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2169#endif
2170
2171    uint32_t responses = 1;
2172
2173    // initialise RPC descriptor header
2174    rpc_desc_t  rpc;
2175    rpc.index    = RPC_KCM_ALLOC;
2176    rpc.blocking = true;
2177    rpc.rsp      = &responses;
2178
2179    // set input arguments in RPC descriptor
2180    rpc.args[0] = (uint64_t)kmem_type;
2181
2182    // register RPC request in remote RPC fifo
2183    rpc_send( cxy , &rpc );
2184
2185    // get output arguments from RPC descriptor
2186    *buf_xp = (xptr_t)rpc.args[1];
2187
2188#if DEBUG_RPC_KCM_ALLOC
2189cycle = (uint32_t)hal_get_cycles();
2190if( cycle > DEBUG_RPC_KCM_ALLOC )
2191printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2192__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2193#endif
2194}
2195
2196//////////////////////////////////////
2197void rpc_kcm_alloc_server( xptr_t xp )
2198{
2199#if DEBUG_RPC_KCM_ALLOC
2200thread_t * this = CURRENT_THREAD;
2201uint32_t cycle = (uint32_t)hal_get_cycles();
2202if( cycle > DEBUG_RPC_KCM_ALLOC )
2203printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2204__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2205#endif
2206
2207    // get client cluster identifier and pointer on RPC descriptor
2208    cxy_t        client_cxy  = GET_CXY( xp );
2209    rpc_desc_t * desc        = GET_PTR( xp );
2210
2211    // get input argument "kmem_type" from client RPC descriptor
2212    uint32_t kmem_type = (uint32_t)hal_remote_l64( XPTR( client_cxy , &desc->args[0] ) );
2213
2214    // allocates memory for kcm
2215    kmem_req_t  req;
2216    req.type  = kmem_type;
2217    req.flags = AF_ZERO;
2218    void * buf_ptr = kmem_alloc( &req );
2219
2220    // set output argument
2221    xptr_t buf_xp = XPTR( local_cxy , buf_ptr );
2222    hal_remote_s64( XPTR( client_cxy , &desc->args[1] ) , (uint64_t)buf_xp );
2223
2224#if DEBUG_RPC_KCM_ALLOC
2225cycle = (uint32_t)hal_get_cycles();
2226if( cycle > DEBUG_RPC_KCM_ALLOC )
2227printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2228__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2229#endif
2230}   
2231*/
2232
2233/////////////////////////////////////////////////////////////////////////////////////////
2234// [23]          RPC_KCM_FREE deprecated [AG] sept 2019
2235/////////////////////////////////////////////////////////////////////////////////////////
2236
2237/*
2238/////////////////////////////////////////
2239void rpc_kcm_free_client( cxy_t      cxy,
2240                          void     * buf,          // in
2241                          uint32_t   kmem_type )   // in
2242{
2243#if DEBUG_RPC_KCM_FREE
2244thread_t * this = CURRENT_THREAD;
2245uint32_t cycle = (uint32_t)hal_get_cycles();
2246if( cycle > DEBUG_RPC_KCM_FREE )
2247printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2248__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2249#endif
2250
2251    uint32_t responses = 1;
2252
2253    // initialise RPC descriptor header
2254    rpc_desc_t  rpc;
2255    rpc.index    = RPC_KCM_FREE;
2256    rpc.blocking = true;
2257    rpc.rsp      = &responses;
2258
2259    // set input arguments in RPC descriptor
2260    rpc.args[0] = (uint64_t)(intptr_t)buf;
2261    rpc.args[1] = (uint64_t)kmem_type;
2262
2263    // register RPC request in remote RPC fifo
2264    rpc_send( cxy , &rpc );
2265
2266#if DEBUG_RPC_KCM_FREE
2267cycle = (uint32_t)hal_get_cycles();
2268if( cycle > DEBUG_RPC_KCM_FREE )
2269printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2270__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2271#endif
2272}
2273
2274/////////////////////////////////////
2275void rpc_kcm_free_server( xptr_t xp )
2276{
2277#if DEBUG_RPC_KCM_FREE
2278thread_t * this = CURRENT_THREAD;
2279uint32_t cycle = (uint32_t)hal_get_cycles();
2280if( cycle > DEBUG_RPC_KCM_FREE )
2281printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2282__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2283#endif
2284
2285    // get client cluster identifier and pointer on RPC descriptor
2286    cxy_t        client_cxy  = GET_CXY( xp );
2287    rpc_desc_t * desc        = GET_PTR( xp );
2288
2289    // get input arguments "buf" and "kmem_type" from client RPC descriptor
2290    void     * buf = (void *)(intptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[0] ) );
2291    uint32_t   kmem_type = (uint32_t)hal_remote_l64( XPTR( client_cxy , &desc->args[1] ) );
2292
2293    // releases memory
2294    kmem_req_t  req;
2295    req.type = kmem_type;
2296    req.ptr  = buf;
2297    kmem_free( &req );
2298
2299#if DEBUG_RPC_KCM_FREE
2300cycle = (uint32_t)hal_get_cycles();
2301if( cycle > DEBUG_RPC_KCM_FREE )
2302printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2303__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2304#endif
2305}   
2306*/
2307
2308/////////////////////////////////////////////////////////////////////////////////////////
2309// [24]          Marshaling functions attached to RPC_MAPPER_SYNC
2310/////////////////////////////////////////////////////////////////////////////////////////
2311
2312///////////////////////////////////////////////////
2313void rpc_mapper_sync_client( cxy_t             cxy,
2314                             struct mapper_s * mapper,
2315                             error_t         * error )
2316{
2317#if DEBUG_RPC_MAPPER_SYNC
2318thread_t * this = CURRENT_THREAD;
2319uint32_t cycle = (uint32_t)hal_get_cycles();
2320if( cycle > DEBUG_RPC_MAPPER_SYNC )
2321printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2322__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2323#endif
2324
2325    uint32_t responses = 1;
2326
2327    // initialise RPC descriptor header
2328    rpc_desc_t  rpc;
2329    rpc.index    = RPC_MAPPER_SYNC;
2330    rpc.blocking = true;
2331    rpc.rsp      = &responses;
2332
2333    // set input arguments in RPC descriptor
2334    rpc.args[0] = (uint64_t)(intptr_t)mapper;
2335
2336    // register RPC request in remote RPC fifo
2337    rpc_send( cxy , &rpc );
2338
2339    // get output values from RPC descriptor
2340    *error   = (error_t)rpc.args[1];
2341
2342#if DEBUG_RPC_MAPPER_SYNC
2343cycle = (uint32_t)hal_get_cycles();
2344if( cycle > DEBUG_RPC_MAPPER_SYNC )
2345printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2346__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2347#endif
2348}
2349
2350////////////////////////////////////////
2351void rpc_mapper_sync_server( xptr_t xp )
2352{
2353#if DEBUG_RPC_MAPPER_SYNC
2354thread_t * this = CURRENT_THREAD;
2355uint32_t cycle = (uint32_t)hal_get_cycles();
2356if( cycle > DEBUG_RPC_MAPPER_SYNC )
2357printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2358__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2359#endif
2360
2361    mapper_t * mapper;
2362    error_t    error;
2363
2364    // get client cluster identifier and pointer on RPC descriptor
2365    cxy_t        client_cxy  = GET_CXY( xp );
2366    rpc_desc_t * desc        = GET_PTR( xp );
2367
2368    // get arguments from client RPC descriptor
2369    mapper  = (mapper_t *)(intptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[0] ) );
2370
2371    // call local kernel function
2372    error = mapper_sync( mapper );
2373
2374    // set output argument to client RPC descriptor
2375    hal_remote_s64( XPTR( client_cxy , &desc->args[1] ) , (uint64_t)error );
2376
2377#if DEBUG_RPC_MAPPER_SYNC
2378cycle = (uint32_t)hal_get_cycles();
2379if( cycle > DEBUG_RPC_MAPPER_SYNC )
2380printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2381__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2382#endif
2383}
2384
2385/////////////////////////////////////////////////////////////////////////////////////////
2386// [25]          Marshaling functions attached to RPC_VMM_RESIZE_VSEG
2387/////////////////////////////////////////////////////////////////////////////////////////
2388
2389//////////////////////////////////////////////////////////
2390void rpc_vmm_resize_vseg_client( cxy_t             cxy,
2391                                 struct process_s * process,
2392                                 struct vseg_s    * vseg,
2393                                 intptr_t           new_base,
2394                                 intptr_t           new_size )
2395{
2396#if DEBUG_RPC_VMM_RESIZE_VSEG
2397thread_t * this = CURRENT_THREAD;
2398uint32_t cycle = (uint32_t)hal_get_cycles();
2399if( cycle > DEBUG_RPC_VMM_RESIZE_VSEG )
2400printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2401__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2402#endif
2403
2404    uint32_t responses = 1;
2405
2406    // initialise RPC descriptor header
2407    rpc_desc_t  rpc;
2408    rpc.index    = RPC_VMM_RESIZE_VSEG;
2409    rpc.blocking = true;
2410    rpc.rsp      = &responses;
2411
2412    // set input arguments in RPC descriptor
2413    rpc.args[0] = (uint64_t)(intptr_t)process;
2414    rpc.args[1] = (uint64_t)(intptr_t)vseg;
2415    rpc.args[2] = (uint64_t)new_base;
2416    rpc.args[3] = (uint64_t)new_size;
2417
2418    // register RPC request in remote RPC fifo
2419    rpc_send( cxy , &rpc );
2420
2421#if DEBUG_RPC_VMM_RESIZE_VSEG
2422cycle = (uint32_t)hal_get_cycles();
2423if( cycle > DEBUG_RPC_VMM_RESIZE_VSEG )
2424printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2425__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2426#endif
2427}
2428
2429////////////////////////////////////////////
2430void rpc_vmm_resize_vseg_server( xptr_t xp )
2431{
2432#if DEBUG_RPC_VMM_RESIZE_VSEG
2433thread_t * this = CURRENT_THREAD;
2434uint32_t cycle = (uint32_t)hal_get_cycles();
2435if( cycle > DEBUG_RPC_VMM_RESIZE_VSEG )
2436printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2437__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2438#endif
2439
2440    process_t * process;
2441    vseg_t    * vseg;
2442    intptr_t    new_base;
2443    intptr_t    new_size;
2444
2445    // get client cluster identifier and pointer on RPC descriptor
2446    cxy_t        client_cxy  = GET_CXY( xp );
2447    rpc_desc_t * desc        = GET_PTR( xp );
2448
2449    // get arguments from client RPC descriptor
2450    process  = (process_t *)(intptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[0] ) );
2451    vseg     = (vseg_t    *)(intptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[1] ) );
2452    new_base =              (intptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[2] ) );
2453    new_size =              (intptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[3] ) );
2454
2455    // call relevant kernel function
2456    vmm_resize_vseg( process,
2457                     vseg,
2458                     new_base,
2459                     new_size );
2460
2461#if DEBUG_RPC_VMM_RESIZE_VSEG
2462cycle = (uint32_t)hal_get_cycles();
2463if( cycle > DEBUG_RPC_VMM_RESIZE_VSEG )
2464printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2465__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2466#endif
2467}
2468
2469
2470/////////////////////////////////////////////////////////////////////////////////////////
2471// [26]  Marshaling functions attached to RPC_VMM_REMOVE_VSEG
2472/////////////////////////////////////////////////////////////////////////////////////////
2473
2474/////////////////////////////////////////////////
2475void rpc_vmm_remove_vseg_client( cxy_t       cxy,
2476                                 process_t * process,
2477                                 vseg_t    * vseg )
2478{
2479#if DEBUG_RPC_VMM_REMOVE_VSEG
2480thread_t * this  = CURRENT_THREAD;
2481uint32_t   cycle = (uint32_t)hal_get_cycles();
2482if( cycle > DEBUG_RPC_VMM_REMOVE_VSEG )
2483printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2484__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
2485#endif
2486
2487    uint32_t    responses = 1;
2488    rpc_desc_t  rpc;
2489
2490    // initialise RPC descriptor header
2491    rpc.index    = RPC_VMM_REMOVE_VSEG;
2492    rpc.blocking = true;
2493    rpc.rsp      = &responses;
2494
2495    // set input arguments in RPC descriptor
2496    rpc.args[0] = (uint64_t)(intptr_t)process;
2497    rpc.args[1] = (uint64_t)(intptr_t)vseg;
2498
2499    // register RPC request in remote RPC fifo
2500    rpc_send( cxy , &rpc );
2501
2502#if DEBUG_RPC_VMM_REMOVE_VSEG
2503cycle = (uint32_t)hal_get_cycles();
2504if( cycle > DEBUG_RPC_VMM_REMOVE_VSEG )
2505printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2506__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
2507#endif
2508}
2509
2510////////////////////////////////////////////
2511void rpc_vmm_remove_vseg_server( xptr_t xp )
2512{
2513#if DEBUG_RPC_VMM_REMOVE_VSEG
2514uint32_t cycle = (uint32_t)hal_get_cycles();
2515thread_t * this = CURRENT_THREAD;
2516if( DEBUG_RPC_VMM_REMOVE_VSEG < cycle )
2517printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2518__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
2519#endif
2520
2521    process_t * process;
2522    vseg_t    * vseg;
2523
2524    // get client cluster identifier and pointer on RPC descriptor
2525    cxy_t        client_cxy = GET_CXY( xp );
2526    rpc_desc_t * desc       = GET_PTR( xp );
2527
2528    // get arguments from RPC descriptor
2529    process  = (process_t *)(intptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[0] ) );
2530    vseg     = (vseg_t    *)(intptr_t)hal_remote_l64( XPTR( client_cxy , &desc->args[1] ) );
2531
2532    // call relevant kernel function
2533    vmm_remove_vseg( process,
2534                     vseg );
2535
2536#if DEBUG_RPC_VMM_REMOVE_VSEG
2537cycle = (uint32_t)hal_get_cycles();
2538if( DEBUG_RPC_VMM_REMOVE_VSEG < cycle )
2539printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2540__FUNCTION__, this->process->pid, this->trdid, this->core->lid, cycle );
2541#endif
2542} 
2543
2544/////////////////////////////////////////////////////////////////////////////////////////
2545// [27]          Marshaling functions attached to RPC_VMM_CREATE_VSEG
2546/////////////////////////////////////////////////////////////////////////////////////////
2547
2548////////////////////////////////////////////////////////
2549void rpc_vmm_create_vseg_client( cxy_t              cxy,
2550                                 struct process_s * process,
2551                                 vseg_type_t        type,
2552                                 intptr_t           base,
2553                                 uint32_t           size,
2554                                 uint32_t           file_offset,
2555                                 uint32_t           file_size,
2556                                 xptr_t             mapper_xp,
2557                                 cxy_t              vseg_cxy,
2558                                 struct vseg_s   ** vseg )
2559{
2560#if DEBUG_RPC_VMM_CREATE_VSEG
2561thread_t * this = CURRENT_THREAD;
2562uint32_t cycle = (uint32_t)hal_get_cycles();
2563if( cycle > DEBUG_RPC_VMM_CREATE_VSEG )
2564printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2565__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2566#endif
2567
2568    uint32_t responses = 1;
2569
2570    // initialise RPC descriptor header
2571    rpc_desc_t  rpc;
2572    rpc.index    = RPC_VMM_CREATE_VSEG;
2573    rpc.blocking = true;
2574    rpc.rsp      = &responses;
2575
2576    // set input arguments in RPC descriptor
2577    rpc.args[0] = (uint64_t)(intptr_t)process;
2578    rpc.args[1] = (uint64_t)type;
2579    rpc.args[2] = (uint64_t)base;
2580    rpc.args[3] = (uint64_t)size;
2581    rpc.args[4] = (uint64_t)file_offset;
2582    rpc.args[5] = (uint64_t)file_size;
2583    rpc.args[6] = (uint64_t)mapper_xp;
2584    rpc.args[7] = (uint64_t)vseg_cxy;
2585
2586    // register RPC request in remote RPC fifo
2587    rpc_send( cxy , &rpc );
2588
2589    // get output values from RPC descriptor
2590    *vseg = (vseg_t *)(intptr_t)rpc.args[8];
2591
2592#if DEBUG_RPC_VMM_CREATE_VSEG
2593cycle = (uint32_t)hal_get_cycles();
2594if( cycle > DEBUG_RPC_VMM_CREATE_VSEG )
2595printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2596__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2597#endif
2598}
2599
2600////////////////////////////////////////////
2601void rpc_vmm_create_vseg_server( xptr_t xp )
2602{
2603#if DEBUG_RPC_VMM_CREATE_VSEG
2604thread_t * this = CURRENT_THREAD;
2605uint32_t cycle = (uint32_t)hal_get_cycles();
2606if( cycle > DEBUG_RPC_VMM_CREATE_VSEG )
2607printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2608__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2609#endif
2610
2611    // get client cluster identifier and pointer on RPC descriptor
2612    cxy_t        cxy  = GET_CXY( xp );
2613    rpc_desc_t * desc = GET_PTR( xp );
2614
2615    // get input arguments from client RPC descriptor
2616    process_t * process     = (process_t *)(intptr_t)hal_remote_l64( XPTR(cxy , &desc->args[0]));
2617    vseg_type_t type        = (vseg_type_t)(uint32_t)hal_remote_l64( XPTR(cxy , &desc->args[1]));
2618    intptr_t    base        = (intptr_t)             hal_remote_l64( XPTR(cxy , &desc->args[2]));
2619    uint32_t    size        = (uint32_t)             hal_remote_l64( XPTR(cxy , &desc->args[3]));
2620    uint32_t    file_offset = (uint32_t)             hal_remote_l64( XPTR(cxy , &desc->args[4]));
2621    uint32_t    file_size   = (uint32_t)             hal_remote_l64( XPTR(cxy , &desc->args[5]));
2622    xptr_t      mapper_xp   = (xptr_t)               hal_remote_l64( XPTR(cxy , &desc->args[6]));
2623    cxy_t       vseg_cxy    = (cxy_t)(uint32_t)      hal_remote_l64( XPTR(cxy , &desc->args[7]));
2624   
2625    // call local kernel function
2626    vseg_t * vseg = vmm_create_vseg( process,
2627                                     type,
2628                                     base,
2629                                     size,
2630                                     file_offset,
2631                                     file_size,
2632                                     mapper_xp,
2633                                     vseg_cxy ); 
2634
2635    // set output arguments into client RPC descriptor
2636    hal_remote_s64( XPTR( cxy , &desc->args[8] ) , (uint64_t)(intptr_t)vseg );
2637
2638#if DEBUG_RPC_VMM_CREATE_VSEG
2639cycle = (uint32_t)hal_get_cycles();
2640if( cycle > DEBUG_RPC_VMM_CREATE_VSEG )
2641printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2642__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2643#endif
2644}
2645
2646/////////////////////////////////////////////////////////////////////////////////////////
2647// [28]          Marshaling functions attached to RPC_VMM_SET_COW
2648/////////////////////////////////////////////////////////////////////////////////////////
2649
2650/////////////////////////////////////////////
2651void rpc_vmm_set_cow_client( cxy_t       cxy,
2652                             process_t * process )
2653{
2654#if DEBUG_RPC_VMM_SET_COW
2655thread_t * this = CURRENT_THREAD;
2656uint32_t cycle = (uint32_t)hal_get_cycles();
2657if( cycle > DEBUG_RPC_VMM_SET_COW )
2658printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2659__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2660#endif
2661
2662    uint32_t responses = 1;
2663
2664    // initialise RPC descriptor header
2665    rpc_desc_t  rpc;
2666    rpc.index    = RPC_VMM_SET_COW;
2667    rpc.blocking = true;
2668    rpc.rsp      = &responses;
2669
2670    // set input arguments in RPC descriptor
2671    rpc.args[0] = (uint64_t)(intptr_t)process;
2672
2673    // register RPC request in remote RPC fifo
2674    rpc_send( cxy , &rpc );
2675
2676#if DEBUG_RPC_VMM_SET_COW
2677cycle = (uint32_t)hal_get_cycles();
2678if( cycle > DEBUG_RPC_VMM_SET_COW )
2679printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2680__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2681#endif
2682}
2683
2684////////////////////////////////////////
2685void rpc_vmm_set_cow_server( xptr_t xp )
2686{
2687#if DEBUG_RPC_VMM_SET_COW
2688thread_t * this = CURRENT_THREAD;
2689uint32_t cycle = (uint32_t)hal_get_cycles();
2690if( cycle > DEBUG_RPC_VMM_SET_COW )
2691printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2692__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2693#endif
2694
2695    process_t * process;
2696
2697    // get client cluster identifier and pointer on RPC descriptor
2698    cxy_t        cxy  = GET_CXY( xp );
2699    rpc_desc_t * desc = GET_PTR( xp );
2700
2701    // get input arguments from client RPC descriptor
2702    process = (process_t *)(intptr_t)hal_remote_l64( XPTR(cxy , &desc->args[0]));
2703   
2704    // call local kernel function
2705    vmm_set_cow( process );
2706
2707#if DEBUG_RPC_VMM_SET_COW
2708cycle = (uint32_t)hal_get_cycles();
2709if( cycle > DEBUG_RPC_VMM_SET_COW )
2710printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2711__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2712#endif
2713}
2714
2715/////////////////////////////////////////////////////////////////////////////////////////
2716// [29]      RPC_VMM_DISPLAY deprecated [AG] June 2019
2717/////////////////////////////////////////////////////////////////////////////////////////
2718
2719/*
2720/////////////////////////////////////////////
2721void rpc_hal_vmm_display_client( cxy_t       cxy,
2722                             process_t * process,
2723                             bool_t      detailed )
2724{
2725#if DEBUG_RPC_VMM_DISPLAY
2726thread_t * this = CURRENT_THREAD;
2727uint32_t cycle = (uint32_t)hal_get_cycles();
2728if( cycle > DEBUG_RPC_VMM_DISPLAY )
2729printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2730__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2731#endif
2732
2733    uint32_t responses = 1;
2734
2735    // initialise RPC descriptor header
2736    rpc_desc_t  rpc;
2737    rpc.index    = RPC_VMM_DISPLAY;
2738    rpc.blocking = true;
2739    rpc.rsp      = &responses;
2740
2741    // set input arguments in RPC descriptor
2742    rpc.args[0] = (uint64_t)(intptr_t)process;
2743    rpc.args[1] = (uint64_t)detailed;
2744
2745    // register RPC request in remote RPC fifo
2746    rpc_send( cxy , &rpc );
2747
2748#if DEBUG_RPC_VMM_DISPLAY
2749cycle = (uint32_t)hal_get_cycles();
2750if( cycle > DEBUG_RPC_VMM_DISPLAY )
2751printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2752__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2753#endif
2754}
2755
2756////////////////////////////////////////
2757void rpc_hal_vmm_display_server( xptr_t xp )
2758{
2759#if DEBUG_RPC_VMM_DISPLAY
2760thread_t * this = CURRENT_THREAD;
2761uint32_t cycle = (uint32_t)hal_get_cycles();
2762if( cycle > DEBUG_RPC_VMM_DISPLAY )
2763printk("\n[%s] thread[%x,%x] on core %d enter / cycle %d\n",
2764__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2765#endif
2766
2767    process_t * process;
2768    bool_t      detailed;
2769
2770    // get client cluster identifier and pointer on RPC descriptor
2771    cxy_t        cxy  = GET_CXY( xp );
2772    rpc_desc_t * desc = GET_PTR( xp );
2773
2774    // get input arguments from client RPC descriptor
2775    process  = (process_t *)(intptr_t)hal_remote_l64( XPTR(cxy , &desc->args[0]));
2776    detailed = (bool_t)               hal_remote_l64( XPTR(cxy , &desc->args[1]));
2777   
2778    // call local kernel function
2779    hal_vmm_display( process , detailed );
2780
2781#if DEBUG_RPC_VMM_DISPLAY
2782cycle = (uint32_t)hal_get_cycles();
2783if( cycle > DEBUG_RPC_VMM_DISPLAY )
2784printk("\n[%s] thread[%x,%x] on core %d exit / cycle %d\n",
2785__FUNCTION__, this->process->pid, this->trdid, this->core->lid , cycle );
2786#endif
2787}
2788
2789*/
Note: See TracBrowser for help on using the repository browser.