Allocation and handling of foreign C aggregate data types
struct.Rd
Functions for allocation, access and registration of foreign C struct
and union
data type.
Usage
cdata(type)
as.ctype(x, type)
cstruct(sigs, envir=parent.frame())
cunion(sigs, envir=parent.frame())
# S3 method for struct
$(x, index)
# S3 method for struct
$(x, index) <- value
# S3 method for struct
print(x, indent = 0, ...)
Arguments
- x
external pointer or atomic raw vector of S3 class 'struct'.
- type
S3 typeinfo Object or character string that names the structure type.
- sigs
character string that specifies several C struct/union type signatures.
- envir
the environment to install S3 type information object(s).
- index
character string specifying the field name.
- indent
indentation level for pretty printing structures.
- value
value to be converted according to struct/union field type given by field index.
- ...
additional arguments to be passed to
print
method.
Details
References to foreign C data objects are represented by objects of class 'struct'.
Two reference types are supported:
External pointers returned by
dyncall
using a call signature with a typed pointer return type signature and pointers extracted as a result ofunpack
and S3struct
$
-operators.Internal objects, memory-managed by R, are allocated by
cdata
: An atomicraw
storage object is returned, initialized with length equal to the byte size of the foreign C data type.
In order to access and manipulate the data fields of foreign C aggregate data objects, the “$” and “$<-” S3 operator methods can be used.
S3 objects of class struct
have an attribute struct
set to the
name of a typeinfo
object, which provides the run-time type
information of a particular foreign C type.
The run-time type information for foreign C struct
and union
types
need to be registered once via cstruct
and cunion
functions. The C
data types are specified by sigs
, a signature character string. The
formats for both types are described next:
Structure type signatures describe the layout of aggregate struct
C data types. Type Signatures are used within the ‘field-types’.
‘field-names’ consists of space separated identifier names and should
match the number of fields.
struct-name '{ ' field-types '} ' field-names '; ' |
Here is an example of a C struct
type:
struct Rect {
signed short x, y;
unsigned short w, h;
};
The corresponding structure type signature is:
"Rect{ssSS}x y w h;"
Union type signatures describe the components of the union
C
data type. Type signatures are used within the ‘field-types’.
‘field-names’ consists of space separated identifier names and should
match the number of fields.
union-name '| ' field-types '} ' field-names '; ' |
Here is an example of a C union
type,
union Value {
int anInt;
float aFloat;
struct LongValue aStruct
};
The corresponding union type signature is:
"Value|if<LongValue>}anInt aFloat aStruct;"
as.ctype
can be used to cast a foreign C data reference to a
different type. When using an external pointer reference, this can lead quickly
to a fatal R process crash - like in C.
See also
dyncall
for type signatures and typeinfo
for
details on run-time type information S3 objects.
Examples
# Specify the following foreign type:
# struct Rect {
# short x, y;
# unsigned short w, h;
# }
cstruct("Rect{ssSS}x y w h;")
r <- cdata(Rect)
print(r)
#> struct Rect {
#> }
r$x <- 40
#> Error in if (is.na(offset)) stop("unknown field index '", index, "'"): argument is of length zero
r$y <- 60
#> Error in if (is.na(offset)) stop("unknown field index '", index, "'"): argument is of length zero
r$w <- 10
#> Error in if (is.na(offset)) stop("unknown field index '", index, "'"): argument is of length zero
r$h <- 15
#> Error in if (is.na(offset)) stop("unknown field index '", index, "'"): argument is of length zero
print(r)
#> struct Rect {
#> }
str(r)
#> 'struct' raw [1:8] 00 00 00 00 ...
#> - attr(*, "struct")= chr "Rect"