我有以下C代码使用libmodbus使用ModbusTCP读取单个设备寄存器:
modbus_t *ctx;
uint16_t tab_reg[16];
ctx = modbus_new_tcp("10.0.1.77", 502);
modbus_read_registers(ctx, 0x20, 2, tab_reg);
printf("reg = %d (0x%X)\n", tab_reg[0], tab_reg[0]);
printf("reg = %d (0x%X)\n", tab_reg[1], tab_reg[1]);
Run Code Online (Sandbox Code Playgroud)
现在尝试使用我生成的Vapi将其切换到Vala,new和read的内容是:
[CCode (cheader_filename = "modbus.h", cname = "modbus_new_tcp")]
public static unowned Modbus.modbus_t create_tcp (string ip_address, int port);
public static int read_registers (Modbus.modbus_t ctx, int addr, int nb, uint16 dest);
[CCode (cheader_filename = "modbus.h")]
Run Code Online (Sandbox Code Playgroud)
翻译的Vala程序是:
class ModbusReadTest : GLib.Object {
unowned Modbus.modbus_t ctx;
public void run () {
uint16 reg = 0x00;
ctx = create_tcp ("10.0.1.77", 502);
Modbus.read_registers (ctx, 0x20, 2, reg);
message ("reg = %d (0x%X)", reg, reg);
Modbus.close(ctx);
}
}
Run Code Online (Sandbox Code Playgroud)
巧合的是,当我将其编译成C代码然后使用gcc编译成二进制文件时,我得到错误:
read-registers-test.c:71:2: warning: passing argument 4 of ‘modbus_read_registers’ makes pointer from integer without a cast [enabled by default]
Run Code Online (Sandbox Code Playgroud)
这并不奇怪.但我不确定如何修改Vapi内容以更接近libmodbus标头中的原型:
int modbus_read_registers(modbus_t *ctx, int addr, int nb, uint16_t *dest);
Run Code Online (Sandbox Code Playgroud)
我尝试过混合使用数组选项并使用'out',但一次只能获得多个单字节寄存器.
谢谢你的任何建议.
read_registers 应该是一个实例方法(在Modbus.modbus_t上)而不是静态方法,并且Modbus.modbus_t应该可以重命名为类似Modbus.Context,create_tcp应该是一个构造函数,而Modbus.close应该是一个自由函数Modbus.Context紧凑类,但这不是问题的重点(如果你在irc.gnome.org上停止#vala,你可以得到这些东西的帮助).
你可能想把它变成一个数组:
public static int read_registers (Modbus.modbus_t ctx, int addr, [CCode (array_length_pos = 2.5)] uint16[] dest);
Run Code Online (Sandbox Code Playgroud)
然后你会在Vala做类似的事情:
public void run () {
uint16 reg[2];
ctx = create_tcp ("10.0.1.77", 502);
Modbus.read_registers (ctx, 0x20, reg);
message ("reg = %d (0x%X)", reg, reg);
Modbus.close(ctx);
}
Run Code Online (Sandbox Code Playgroud)
对于更忠实于原始C的端口(其中tab_reg有16个元素而不是2个),您可以使用数组切片:
public void run () {
uint16 reg[16];
ctx = create_tcp ("10.0.1.77", 502);
Modbus.read_registers (ctx, 0x20, reg[0:2]);
stdout.printf ("reg = %d (0x%X)\n", reg, reg);
Modbus.close(ctx);
}
Run Code Online (Sandbox Code Playgroud)
请注意,如果您将其设为实例方法,则需要将array_length_pos更改为1.5.
| 归档时间: |
|
| 查看次数: |
355 次 |
| 最近记录: |