- Configure kernel-only paging with separate user virtual regions - Add PHP Nano project compilation with link library support - Implement aligned memory block management for Zend allocator - Create reusable libtypephp-os.a platform archive for TypePHP userspace - Add uname system call support and update user-space syscalls - Increase QEMU memory allocation from 128M to 160M - Add TNHELLO.ELF as full TypePHP + PHPXmaster
parent
fc826df3d7
commit
2d052429ca
29 changed files with 474 additions and 80 deletions
@ -0,0 +1,20 @@ |
||||
#ifndef TYPEPHP_OS_USER_SYS_UTSNAME_H |
||||
#define TYPEPHP_OS_USER_SYS_UTSNAME_H |
||||
|
||||
#define _UTSNAME_LENGTH 65 |
||||
|
||||
/* Keep the Linux new_utsname layout so the syscall remains compatible with
|
||||
* the interface expected by a future glibc userspace. POSIX exposes the first |
||||
* five fields; domainname is the Linux extension at the end of the ABI. */ |
||||
struct utsname { |
||||
char sysname[_UTSNAME_LENGTH]; |
||||
char nodename[_UTSNAME_LENGTH]; |
||||
char release[_UTSNAME_LENGTH]; |
||||
char version[_UTSNAME_LENGTH]; |
||||
char machine[_UTSNAME_LENGTH]; |
||||
char domainname[_UTSNAME_LENGTH]; |
||||
}; |
||||
|
||||
int uname(struct utsname *value); |
||||
|
||||
#endif |
||||
@ -0,0 +1,36 @@ |
||||
# TypePHP userspace runtime |
||||
|
||||
This directory contains the TypePHP-OS platform layer shared by all |
||||
tpc-generated userspace programs. The top-level Makefile compiles it, the |
||||
kernel ABI shims, and OpenLibm into: |
||||
|
||||
```text |
||||
build/libtypephp-os.a |
||||
``` |
||||
|
||||
Build the archive once with: |
||||
|
||||
```shell |
||||
make user-runtime |
||||
``` |
||||
|
||||
A TypePHP project should contain only its own application sources and link the |
||||
shared archive through its project file: |
||||
|
||||
```yaml |
||||
link-paths: |
||||
- ../../build |
||||
link-libs: |
||||
- typephp-os |
||||
- gcc |
||||
``` |
||||
|
||||
The archive owns the userspace `_start`, PHP Nano host entry, syscall bridge, |
||||
POSIX/libc and C++ ABI shims, and math implementation. Application projects |
||||
must not compile private copies of these files. This allows any number of |
||||
projects under `user/` to reuse one platform archive and keeps their generated |
||||
object directories independent. |
||||
|
||||
The archive and each consumer must use the same freestanding ABI flags and |
||||
PHP Nano/PHPX feature definitions. Those shared settings are maintained in the |
||||
top-level Makefile and the consumer project file respectively. |
||||
@ -0,0 +1,76 @@ |
||||
#include <stddef.h> |
||||
#include <string.h> |
||||
#include <sys/utsname.h> |
||||
#include <unistd.h> |
||||
|
||||
enum uname_field { |
||||
FIELD_SYSNAME = 1u << 0, |
||||
FIELD_NODENAME = 1u << 1, |
||||
FIELD_RELEASE = 1u << 2, |
||||
FIELD_VERSION = 1u << 3, |
||||
FIELD_MACHINE = 1u << 4, |
||||
FIELD_ALL = FIELD_SYSNAME | FIELD_NODENAME | FIELD_RELEASE |
||||
| FIELD_VERSION | FIELD_MACHINE, |
||||
}; |
||||
|
||||
static int select_option(char option, unsigned int *fields) |
||||
{ |
||||
switch (option) { |
||||
case 'a': *fields |= FIELD_ALL; return 1; |
||||
case 's': *fields |= FIELD_SYSNAME; return 1; |
||||
case 'n': *fields |= FIELD_NODENAME; return 1; |
||||
case 'r': *fields |= FIELD_RELEASE; return 1; |
||||
case 'v': *fields |= FIELD_VERSION; return 1; |
||||
case 'm': *fields |= FIELD_MACHINE; return 1; |
||||
default: return 0; |
||||
} |
||||
} |
||||
|
||||
static void print_field(const char *value, int *first) |
||||
{ |
||||
if (!*first) { |
||||
(void) write(STDOUT_FILENO, " ", 1); |
||||
} |
||||
(void) write(STDOUT_FILENO, value, strlen(value)); |
||||
*first = 0; |
||||
} |
||||
|
||||
int main(int argc, char **argv) |
||||
{ |
||||
struct utsname identity; |
||||
unsigned int fields = 0; |
||||
int argument; |
||||
int first = 1; |
||||
|
||||
for (argument = 1; argument < argc; ++argument) { |
||||
const char *option = argv[argument]; |
||||
size_t index; |
||||
if (option[0] != '-' || option[1] == '\0') { |
||||
(void) write(STDERR_FILENO, "uname: invalid argument\n", |
||||
sizeof("uname: invalid argument\n") - 1); |
||||
return 1; |
||||
} |
||||
for (index = 1; option[index] != '\0'; ++index) { |
||||
if (!select_option(option[index], &fields)) { |
||||
(void) write(STDERR_FILENO, "uname: invalid option\n", |
||||
sizeof("uname: invalid option\n") - 1); |
||||
return 1; |
||||
} |
||||
} |
||||
} |
||||
if (fields == 0) { |
||||
fields = FIELD_SYSNAME; |
||||
} |
||||
if (uname(&identity) < 0) { |
||||
(void) write(STDERR_FILENO, "uname: system information unavailable\n", |
||||
sizeof("uname: system information unavailable\n") - 1); |
||||
return 1; |
||||
} |
||||
if ((fields & FIELD_SYSNAME) != 0) print_field(identity.sysname, &first); |
||||
if ((fields & FIELD_NODENAME) != 0) print_field(identity.nodename, &first); |
||||
if ((fields & FIELD_RELEASE) != 0) print_field(identity.release, &first); |
||||
if ((fields & FIELD_VERSION) != 0) print_field(identity.version, &first); |
||||
if ((fields & FIELD_MACHINE) != 0) print_field(identity.machine, &first); |
||||
(void) write(STDOUT_FILENO, "\n", 1); |
||||
return 0; |
||||
} |
||||
Loading…
Reference in new issue