我有一个第三方C库,它定义了一个类似于的结构:
struct myStruct {
int a;
int b;
char str1[32];
char str2[32];
};
Run Code Online (Sandbox Code Playgroud)
还有一个函数,它接受一个指向这个结构的指针并填充它.我需要我的Perl6本机调用来提供该结构,然后读取结果.
到目前为止,我已经在Perl6中定义了结构:
class myStruct is repr('CStruct') {
has int32 $.a;
has int32 $.b;
has Str $.str1; # Option A: This won't work as Perl won't know what length to allocate
has CArray[uint8] $.str2; # Option B: This makes more sense, but again how to define length?
# Also, would this allocate the array in place, or
# reference an array that is separately allocated (and therefore not …Run Code Online (Sandbox Code Playgroud) 有没有办法在CStruct中声明一个对象数组?
struct my_struct {
int foo;
int bar;
char somestring[80];
};
class My::Struct is repr('CStruct') {
has int32 $.foo;
has int32 $.bar;
???
}
Run Code Online (Sandbox Code Playgroud)
A CArray[uint8]将是一个char *指针,实际上并不在结构中保留空间.
而不是My::Struct.new,我可能自己做内存(而不是My::Struct.new(),我使用一个buf8.allocate(xxx)并保持句柄,所以GC不收割它,nativecast它到My :: Struct),然后我必须使用指针数学来找到里面的字符串结构等,但似乎应该有一个更简单的方法.
即使它没有完全实现,一个简单的方法说"在这里放80个字节,这里是指针",这将是非常好的.
这是" 如何在Perl 6中声明固定大小的本机数组? " 的后续问题.
在那个问题中讨论了如何将固定大小的数组合并到一个CStruct.在这个答案有人建议使用HAS内联CArray的CStruct.当我测试这个想法时,我遇到了一些在问题下面的评论部分无法解决的奇怪行为,所以我决定把它写成一个新问题.这是我的C测试库代码:
slib.c:
#include <stdio.h>
struct myStruct
{
int A;
int B[3];
int C;
};
void use_struct (struct myStruct *s) {
printf("sizeof(struct myStruct): %ld\n", sizeof( struct myStruct ));
printf("sizeof(struct myStruct *): %ld\n", sizeof( struct myStruct *));
printf("A = %d\n", s->A);
printf("B[0] = %d\n", s->B[0]);
printf("B[1] = %d\n", s->B[1]);
printf("B[2] = %d\n", s->B[2]);
printf("C = %d\n", s->C);
}
Run Code Online (Sandbox Code Playgroud)
要使用以下方法生成共享库:
gcc -c -fpic slib.c
gcc -shared -o …Run Code Online (Sandbox Code Playgroud)