php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #80847 CData structs with fields of type struct can't be passed as C function argument
Submitted: 2021-03-08 20:29 UTC Modified: -
From: nawarian at gmail dot com Assigned:
Status: Closed Package: ffi (PECL)
PHP Version: 7.4Git-2021-03-08 (Git) OS: MacOS 10.15.7 (Catalina)
Private report: No CVE-ID: None
Welcome back! If you're the original bug submitter, here's where you can edit the bug or add additional notes.
If you forgot your password, you can retrieve your password here.
Password:
Status:
Package:
Bug Type:
Summary:
From: nawarian at gmail dot com
New email:
PHP Version: OS:

 

 [2021-03-08 20:29 UTC] nawarian at gmail dot com
Description:
------------
Configure line: --without-iconv --with-ffi
PHP Version used: 7.4 (GIT as of 2021-03-08)
Raylib 3.5.0 library installed via HomeBrew: https://github.com/raysan5/raylib/releases/tag/3.5.0

Any struct containing fields of type struct can be normally built, but PHP throws a Fatal Error whenever they are passed.

I found the issue by attempting to run the BeginMode2D() function from raylib. (links below)

This function requires a "struct Camera2D" argument, which itself has two "struct Vector2" fields.

I've attached a patch that mitigates this issue but generates many memory leaks that I don't really know how to mitigate.

---
Hints:

I found that "zend_ffi_make_fake_struct_type" doesn't have a "case ZEND_FFI_TYPE_STRUCT" when iterating over a record's fields, forcing the function to return NULL.

---
Links:

function BeginMode2D(): https://github.com/raysan5/raylib/blob/3.5.0/src/raylib.h#L943

struct Camera2D: https://github.com/raysan5/raylib/blob/3.5.0/src/raylib.h#L299-L304

struct Vector2D: https://github.com/raysan5/raylib/blob/3.5.0/src/raylib.h#L173-L176

Test script:
---------------
A minimal script can be found in this URL: https://gist.github.com/nawarian/319d363dacea2feebc409e5413d03887

Notice that PHP is able to construct CData objects with structs inside. But using them as function argument creates a Fatal Error.

Expected result:
----------------
A native window with dimensions 800x600 and title "Nawarian" and blinking content (black / white) should appear.

Actual result:
--------------
Fatal error: Uncaught FFI\Exception: Passing incompatible argument 1 of C function 'BeginMode2D', expecting 'struct Camera2D', found 'struct Camera2D' in /Users/nsilva/RG/personal/test-ffi/raylib.php:11

Stack trace:
#0 /Users/nsilva/RG/personal/test-ffi/raylib.php(11): FFI->BeginMode2D(Object(FFI\CData:struct Camera2D))
#1 {main}
  thrown in /Users/nsilva/RG/personal/test-ffi/raylib.php on line 11

Patches

incomplete-solution (last revision 2021-03-08 20:29 UTC by nawarian at gmail dot com)

Pull Requests

Pull requests:

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2021-03-08 20:36 UTC] nawarian at gmail dot com
The following pull request has been associated:

Patch Name: [FFI] Resolve struct type for internal struct fields
On GitHub:  https://github.com/php/php-src/pull/6762
Patch:      https://github.com/php/php-src/pull/6762.patch
 [2021-03-17 06:56 UTC] dmitry@php.net
Automatic comment on behalf of dmitry@zend.com
Revision: http://git.php.net/?p=php-src.git;a=commit;h=38ebb55c7c16486c2603f4df906444ee9d651ad4
Log: Fixed bug #80847 (CData structs with fields of type struct can't be passed as C function argument)
 [2021-03-17 06:56 UTC] dmitry@php.net
-Status: Open +Status: Closed
 
PHP Copyright © 2001-2024 The PHP Group
All rights reserved.
Last updated: Sat Dec 21 15:01:29 2024 UTC