flush
authorMichael Wallner <mike@php.net>
Tue, 10 Nov 2015 19:33:38 +0000 (20:33 +0100)
committerMichael Wallner <mike@php.net>
Tue, 10 Nov 2015 19:33:38 +0000 (20:33 +0100)
Makefile.frag
config.m4
src/context.c
src/module.c
tests/stat/stat.psi [new file with mode: 0644]
tests/stat/stat001.phpt [new file with mode: 0644]
tests/time/time.psi
tests/time/time002.phpt
tests/time/time003.phpt
tests/time/time004.phpt [new file with mode: 0644]

index 1c42778fe48d63213d6d0e85a8effb14cda92227..bca0f48df131013d30981bf5b2d0f0c8bac8b27b 100644 (file)
@@ -25,6 +25,8 @@ lemon.c:
 ./lemon: lemon.c | lempar.c
        $(CC) -o $@ $<
 
+$(PHP_PSI_SRCDIR)/src/context.c: $(PHP_PSI_SRCDIR)/config.m4
+       touch $@
 $(PHP_PSI_SRCDIR)/src/%.c: $(PHP_PSI_BUILDDIR)/parser.h
        touch $@
 $(PHP_PSI_SRCDIR)/src/parser_proc.y: $(PHP_PSI_BUILDDIR)/parser.h
index ee54dac1f5b12d9a809dd7fe0d0771fd0d258ae4..21f997969369e032898c1ef3c3e7d61bf023fd2f 100644 (file)
--- a/config.m4
+++ b/config.m4
@@ -199,6 +199,7 @@ if test "$PHP_PSI" != "no"; then
        dnl PSI_STRUCT(name, members, member type cases, includes)
        PSI_STRUCTS=
        AC_DEFUN(PSI_STRUCT, [
+               AC_CHECK_SIZEOF(struct $1, [], PSI_INCLUDES_DEFAULT($4))
                psi_struct_members=
                m4_foreach(member, [$2], [
                        AC_CHECK_MEMBER(struct $1.member, [
@@ -227,7 +228,7 @@ if test "$PHP_PSI" != "no"; then
                                fi
                        ], [], PSI_INCLUDES_DEFAULT($4))
                ])
-               PSI_STRUCTS="{\"$1\", {$psi_struct_members}}, $PSI_STRUCTS"
+               PSI_STRUCTS="{\"$1\", $ac_cv_sizeof_struct_$1, {$psi_struct_members}}, $PSI_STRUCTS"
        ])
 
        AC_TYPE_INT8_T
@@ -417,6 +418,13 @@ if test "$PHP_PSI" != "no"; then
        PSI_CONST(ITIMER_REAL, int, sys/time.h)
        PSI_CONST(ITIMER_VIRTUAL, int, sys/time.h)
        PSI_CONST(ITIMER_PROF, int, sys/time.h)
+       dnl sys/times.h
+       PSI_STRUCT(tms, [
+               [tms_utime],
+               [tms_stime],
+               [tms_cutime],
+               [tms_cstime]], [
+       ], sys/times.h)
        dnl sys/types.h
        PSI_TYPE(blkcnt_t, int)
        PSI_TYPE(blksize_t, int)
index f0080f753e1ca6ec5aa15b2b5ec559e69e9a707b..83a1a28f34b03f26842d89708972ea4f73fdd007 100644 (file)
@@ -49,6 +49,7 @@ typedef struct psi_predef_struct_member {
 #define PSI_PREDEF_STRUCT_MEMBERS 32
 typedef struct psi_predef_struct {
        const char *name;
+       size_t size;
        psi_predef_struct_member members[PSI_PREDEF_STRUCT_MEMBERS];
 } psi_predef_struct;
 static const psi_predef_struct psi_predef_structs[] = {
@@ -78,7 +79,7 @@ static int validate_lib(PSI_Data *data, void **dlopened) {
        }
        if (!(*dlopened = dlopen(ptr, RTLD_LAZY|RTLD_LOCAL))) {
                data->error(PSI_WARNING, "Could not open library '%s': %s.",
-                               data->psi.file.fn, dlerror());
+                               data->psi.file.ln, dlerror());
                return 0;
        }
        return 1;
@@ -229,7 +230,7 @@ static inline int validate_decl_func(PSI_Data *data, void *dl, decl *decl, decl_
 #endif
        decl->dlptr = dlsym(dl ?: RTLD_NEXT, func->var->name);
        if (!decl->dlptr) {
-               data->error(PSI_WARNING, "Failed to located symbol '%s': %s",
+               data->error(PSI_WARNING, "Failed to locate symbol '%s': %s",
                        func->var->name, dlerror());
        }
        return 1;
@@ -505,6 +506,7 @@ PSI_Context *PSI_ContextInit(PSI_Context *C, PSI_ContextOps *ops, PSI_ContextErr
                }
 
                dstruct = init_decl_struct(pre->name, dargs);
+               dstruct->size = pre->size;
                T.structs = add_decl_struct(T.structs, dstruct);
        }
 
index 3b4a643e2710986b92039992a167990dee058421..6f152e3d750ef3933c56a8b44419752dd314592b 100644 (file)
@@ -332,10 +332,11 @@ void psi_to_array(zval *return_value, token_t t, impl_val *ret_val, decl_var *va
                ZEND_ASSERT(s);
                for (i = 0; i < s->args->count; ++i) {
                        decl_arg *darg = s->args->args[i];
-                       impl_val tmp;
+                       impl_val tmp, tmp_ptr;
                        zval ztmp;
                        char *ptr = (char *) ret_val->ptr + darg->layout->pos;
 
+                       tmp_ptr.ptr = &tmp;
                        memset(&tmp, 0, sizeof(tmp));
                        memcpy(&tmp, ptr, darg->layout->len);
                        switch (real_decl_type(darg->type)->type) {
@@ -358,6 +359,9 @@ void psi_to_array(zval *return_value, token_t t, impl_val *ret_val, decl_var *va
                        case PSI_T_UINT64:
                                psi_to_int(&ztmp, real_decl_type(darg->type)->type, &tmp, darg->var);
                                break;
+                       case PSI_T_STRUCT:
+                               psi_to_array(&ztmp, real_decl_type(darg->type)->type, &tmp_ptr, darg->var);
+                               break;
                        default:
                                printf("t=%d\n", real_decl_type(darg->type)->type);
                                abort();
diff --git a/tests/stat/stat.psi b/tests/stat/stat.psi
new file mode 100644 (file)
index 0000000..0017565
--- /dev/null
@@ -0,0 +1,8 @@
+extern int __xstat64(int ver, char *path, struct stat *buf);
+function psi\stat(string $path, array &$buf = NULL) : int {
+       let ver = NULL;
+       let path = strval($path);
+       let buf = calloc(1, struct stat);
+       return to_int(__xstat64);
+       set $buf = to_array(*buf);
+}
diff --git a/tests/stat/stat001.phpt b/tests/stat/stat001.phpt
new file mode 100644 (file)
index 0000000..c4b4b96
--- /dev/null
@@ -0,0 +1,61 @@
+--TEST--
+stat
+--INI--
+psi.directory={PWD}
+--SKIPIF--
+<?php 
+extension_loaded("psi") or die("skip - need ext/psi");
+?>
+--FILE--
+===TEST===
+<?php 
+var_dump(psi\stat(__FILE__, $stat), $stat);
+?>
+===DONE===
+--EXPECTF--
+===TEST===
+int(0)
+array(13) {
+  ["st_dev"]=>
+  int(%d)
+  ["st_ino"]=>
+  int(%d)
+  ["st_mode"]=>
+  int(%d)
+  ["st_nlink"]=>
+  int(1)
+  ["st_uid"]=>
+  int(%d)
+  ["st_gid"]=>
+  int(%d)
+  ["st_rdev"]=>
+  int(%d)
+  ["st_size"]=>
+  int(76)
+  ["st_atim"]=>
+  array(2) {
+    ["tv_sec"]=>
+    int(1%d)
+    ["tv_nsec"]=>
+    int(%d)
+  }
+  ["st_mtim"]=>
+  array(2) {
+    ["tv_sec"]=>
+    int(1%d)
+    ["tv_nsec"]=>
+    int(%d)
+  }
+  ["st_ctim"]=>
+  array(2) {
+    ["tv_sec"]=>
+    int(1%d)
+    ["tv_nsec"]=>
+    int(%d)
+  }
+  ["st_blksize"]=>
+  int(%d)
+  ["st_blocks"]=>
+  int(%d)
+}
+===DONE===
\ No newline at end of file
index 5b02dc4a5afa80f3eaf42c7c25e2c939b3cf51f2..514d2b3b9a0b17d6eee09fffe064cba9dfc1f828 100644 (file)
@@ -13,13 +13,26 @@ function psi\asctime(array $tm = NULL) : string {
        return to_string(asctime);
 }
 
+extern char *asctime_r(struct tm *tm, char *buf);
+function psi\asctime_r(array $tm = NULL) : string {
+       let tm = arrval($tm);
+       let buf = calloc(32, char);
+       return to_string(asctime_r);
+}
 
-extern struct tm *gmtime(time_t tp);
+extern struct tm *gmtime(time_t *tp);
 function psi\gmtime(int $ts) : array {
        let tp = &intval($ts);
        return to_array(gmtime);
 }
 
+extern struct tm *gmtime_r(time_t *tp, struct tm *buf);
+function psi\gmtime_r(int $ts) : array {
+       let tp = &intval($ts);
+       let buf = calloc(1, struct tm);
+       return to_array(gmtime_r);
+}
+
 extern int nanosleep(struct timespec *rqtp, struct timespec *rmtp);
 function psi\nanosleep(array $rq = NULL, array &$rm = NULL) : int {
        let rqtp = arrval($rq);
@@ -27,3 +40,10 @@ function psi\nanosleep(array $rq = NULL, array &$rm = NULL) : int {
        return to_int(nanosleep);
        set $rm = to_array(*rmtp);
 }
+
+extern clock_t times(struct tms *buf);
+function psi\times(array &$tms = NULL) : int {
+       let buf = calloc(1, struct tms);
+       return to_int(times);
+       set $tms = to_array(*buf);
+}
index 6e091e09d4db87478fc536ed11f2cc9b1a7f6c0d..2bf43228078c5f7069f29a966b9b299dd2923659 100644 (file)
@@ -12,13 +12,19 @@ psi.directory = {PWD}
 ===TEST===
 <?php
 var_dump(psi\asctime(NULL));
+var_dump(psi\asctime_r(NULL));
 var_dump(psi\asctime(psi\gmtime(1234567890)));
+var_dump(psi\asctime_r(psi\gmtime_r(1234567890)));
 ?>
 ===DONE===
 --EXPECT--
 ===TEST===
 string(25) "Sun Jan  0 00:00:00 1900
 "
+string(25) "Sun Jan  0 00:00:00 1900
+"
+string(25) "Fri Feb 13 23:31:30 2009
+"
 string(25) "Fri Feb 13 23:31:30 2009
 "
 ===DONE===
index 1fe5073b676ce7c55fe50cbf99fd74ccf6f578da..ec863bfde15ec2b2abf004e0546c654446e5b7c9 100644 (file)
@@ -40,5 +40,5 @@ array(2) {
   ["tv_usec"]=>
   int(%d)
 }
-int(10%r\d\d\d%r)
+int(%r\d\d\d\d\d%r)
 ===DONE===
diff --git a/tests/time/time004.phpt b/tests/time/time004.phpt
new file mode 100644 (file)
index 0000000..678d4bc
--- /dev/null
@@ -0,0 +1,28 @@
+--TEST--
+times
+--INI--
+psi.directory={PWD}
+--SKIPIF--
+<?php
+extension_loaded("psi") or die("skip - need ext/psi");
+?>
+--FILE--
+===TEST===
+<?php 
+var_dump(psi\times($times), $times);
+?>
+===DONE===
+--EXPECTF--
+===TEST===
+int(%d)
+array(4) {
+  ["tms_utime"]=>
+  int(%d)
+  ["tms_stime"]=>
+  int(%d)
+  ["tms_cutime"]=>
+  int(%d)
+  ["tms_cstime"]=>
+  int(%d)
+}
+===DONE===