Jer*_*emy 2 python sockets udp d
我正在尝试将python程序转换为D; 该程序用于发送Art-Net DMX数据包.
蟒蛇:
import sys, socket, math, time
from ctypes import *
class ArtNetDMXOut(LittleEndianStructure):
PORT = 0x1936
_fields_ = [("id", c_char * 8),
("opcode", c_ushort),
("protverh", c_ubyte),
("protver", c_ubyte),
("sequence", c_ubyte),
("physical", c_ubyte),
("universe", c_ushort),
("lengthhi", c_ubyte),
("length", c_ubyte),
("payload", c_ubyte * 512)]
def __init__(self):
self.id = b"Art-Net"
self.opcode = 0x5000
self.protver = 14
self.universe = 0
self.lengthhi = 2
def main():
hostIP = "localhost"
S = socket.socket(socket.AF_INET,socket.SOCK_DGRAM)
packet = ArtNetDMXOut()
packet.payload[0] = 255
S.sendto(packet, (hostIP, ArtNetDMXOut.PORT))
if __name__ == "__main__":
main()
Run Code Online (Sandbox Code Playgroud)
d:
import std.stdio;
import std.socket;
class ArtNetDMX{
char id[8];
ushort opCode;
ubyte verH;
ubyte ver;
ubyte sequence;
ubyte physical;
ushort universe;
ubyte lengthHi;
ubyte length;
ubyte data[511];
this(){
this.id = "ART-NET0";
this.opCode = 0x5000;
this.ver = 14;
this.universe = 0;
this.lengthHi = 2;
}
}
void main() {
auto s = new UdpSocket();
auto addr = new InternetAddress("localhost", 6454);
s.bind(addr);
ArtNetDMX packet = new ArtNetDMX();
packet.data[0] = 255;
s.send(packet);
};
Run Code Online (Sandbox Code Playgroud)
我的Python代码的工作原理完全如预期,但在DI得到错误function std.socket.Socket.send (const(void)[] buf, SocketFlags flags) is not callable using argument types (ArtNetDMX)的s.send(packet);路线.
我接近这个吗?我究竟做错了什么?
首先,你需要ArtNetDMX成为一个struct,而不是class- 因为D中的类是引用类型,并且不保证类字段布局; 并且由于您通过电线发送它,请指定适当的对齐方式(如果要将每个字段打包在一起,通常为1):
struct ArtNetDMX {
align(1):
....
}
Run Code Online (Sandbox Code Playgroud)
在您的中main,您现在可以在堆栈上分配它的实例:
ArtNetDMX packet; // no `new` required
packet.id = "ART-NET0"; // initialize fields
packet.opCode = 0x5000;
packet.ver = 14;
packet.universe = 0;
packet.lengthHi = 2;
Run Code Online (Sandbox Code Playgroud)
或者,如果您经常执行相同的初始化,请将其移动到一个函数中:
ArtNetDMX createArtNetDMX()
{
ArtNetDMX packet;
packet.id = "ART-NET0";
packet.opCode = 0x5000;
packet.ver = 14;
packet.universe = 0;
packet.lengthHi = 2;
return packet;
}
Run Code Online (Sandbox Code Playgroud)
最后,Socket.send要求其参数为切片(数组或部分).如果您最终一次发送多个数据包,则将数据包放入数组,然后发送数组.
由于您只发送一个数据包,因此可以替换
s.send(packet);
Run Code Online (Sandbox Code Playgroud)
同
s.send((&packet)[0..1]);
Run Code Online (Sandbox Code Playgroud)
这只是将对象转换为1元素切片的安全方法.