Skip to content

[FFI] Allow to pass CData into struct and/or union fields. #11934

Closed
@SerafimArts

Description

@SerafimArts

Feature/Bug

The following code not working now:

<?php

// Boxed scalar
$uint32 = FFI::new('uint32_t');
$uint32->cdata = 0xDEAD_BEEF;

// Struct
$ffi = FFI::new('struct { uint32_t field; }');
$ffi->field = $uint32;

Or more real world usage:

<?php

$ffi = FFI::new('struct { uint64_t field; }');

$value = FFI::new('struct __attribute__((__packed__)) { uint32_t lo; uint32_t hi; }');
$value->lo = 0x42;        // First 32 bytes
$value->hi = 0xDEAD_BEEF; // Second 32 bytes

// Because PHP (x86) does not support uint64.
// On 64-bit PHP, this can be done with binary conversions (int64 -> uint64), 
// but this is not so convenient.
$ffi->field = FFI::cast('uint64_t', FFI::addr($value));

Resulted in this output:

PHP Warning: Object of class FFI\CData could not be converted to int

I think it makes sense to do automatic boxing/unboxing to int, at least in the same way as it is done with GMP. However, I still have no idea how to implement this without breaking backwards compatibility =\\

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions