l4re-base-25.08.0

This commit is contained in:
2025-09-12 15:55:45 +02:00
commit d959eaab98
37938 changed files with 9382688 additions and 0 deletions

View File

@@ -0,0 +1,9 @@
PKGDIR ?= ..
L4DIR ?= $(PKGDIR)/../../..
TARGET = ex_ipc1
SRC_C = ipc_example.c
REQUIRES_LIBS = libpthread
DEPENDS_PKGS = $(REQUIRES_LIBS)
include $(L4DIR)/mk/prog.mk

View File

@@ -0,0 +1,5 @@
# vim:se ft=lua:
local L4 = require("L4");
L4.default_loader:start({}, "rom/ex_ipc1");

View File

@@ -0,0 +1,114 @@
/**
* \file
* \brief Low-level example of communication.
* \author Adam Lackorzynski <adam@os.inf.tu-dresden.de>
*
* This example shows how two threads can exchange data using the L4 IPC
* mechanism. One thread is sending an integer to the other thread which is
* returning the square of the integer. Both values are printed.
*/
/*
* (c) 2008-2009 Author(s)
* economic rights: Technische Universität Dresden (Germany)
*
* This file is part of TUD:OS and distributed under the terms of the
* GNU General Public License 2.
* Please see the COPYING-GPL-2 file for details.
*/
#include <l4/sys/ipc.h>
#include <pthread-l4.h>
#include <unistd.h>
#include <stdio.h>
static pthread_t t2;
/* Thread1 is the initiator thread, i.e. it initiates the IPC calls. In
* other words, it takes the client role. It uses L4 IPC mechanisms to send
* an integer value to thread2 and received a calculation result back. */
static void *thread1_fn(void *arg)
{
l4_msgtag_t tag;
int ipc_error;
unsigned long value = 1;
(void)arg;
while (1)
{
printf("Sending: %ld\n", value);
/* Store the value which we want to have squared in the first message
* register of our UTCB. */
l4_utcb_mr()->mr[0] = value;
/* To an L4 IPC call, i.e. send a message to thread2 and wait for a
* reply from thread2. The '1' in the msgtag denotes that we want to
* transfer one word of our message registers (i.e. MR0). No timeout. */
tag = l4_ipc_call(pthread_l4_cap(t2), l4_utcb(),
l4_msgtag(0, 1, 0, 0), L4_IPC_NEVER);
/* Check for IPC error, if yes, print out the IPC error code, if not,
* print the received result. */
ipc_error = l4_ipc_error(tag, l4_utcb());
if (ipc_error)
fprintf(stderr, "thread1: IPC error: %x\n", ipc_error);
else
printf("Received: %ld\n", l4_utcb_mr()->mr[0]);
/* Wait some time and increment our value. */
sleep(1);
value++;
}
return NULL;
}
/* Thread2 is in the server role, i.e. it waits for requests from others and
* sends back the calculation results. */
static void *thread2_fn(void *arg)
{
l4_msgtag_t tag;
l4_umword_t label;
int ipc_error;
(void)arg;
/* Wait for requests from any thread. No timeout, i.e. wait forever. */
tag = l4_ipc_wait(l4_utcb(), &label, L4_IPC_NEVER);
while (1)
{
/* Check if we had any IPC failure, if yes, print the error code
* and just wait again. */
ipc_error = l4_ipc_error(tag, l4_utcb());
if (ipc_error)
{
fprintf(stderr, "thread2: IPC error: %x\n", ipc_error);
tag = l4_ipc_wait(l4_utcb(), &label, L4_IPC_NEVER);
continue;
}
/* So, the IPC was ok, now take the value out of message register 0
* of the UTCB and store the square of it back to it. */
l4_utcb_mr()->mr[0] = l4_utcb_mr()->mr[0] * l4_utcb_mr()->mr[0];
/* Send the reply and wait again for new messages.
* The '1' in the msgtag indicated that we want to transfer 1 word in
* the message registers (i.e. MR0) */
tag = l4_ipc_reply_and_wait(l4_utcb(), l4_msgtag(0, 1, 0, 0),
&label, L4_IPC_NEVER);
}
return NULL;
}
int main(void)
{
// We will have two threads, one is already running the main function, the
// other (thread2) will be created using pthread_create.
if (pthread_create(&t2, NULL, thread2_fn, NULL))
{
fprintf(stderr, "Thread creation failed\n");
return 1;
}
// Just run thread1 in the main thread
thread1_fn(NULL);
return 0;
}