我尝试实现SMPP客户端,第一个测试是在我进行实时套接字连接后进行绑定。

但是服务器在接收到流时显示HEX错误消息。

SMPP装置

interface
  uses Classes;
Type
 // c octet strings
  TSystemID = string[16];
  TPassword = string[9];
  TSystemType = string[13];
  TAddr = string[21];
  TAddr_Range = string[41];
  TSvc_Type = string[6];
  TDate_time = string[17];
  TMsgID = string[65];
pPDU_HDR = ^TPDU_HDR;

TPDU_HDR = packed record
    command_len : LongWord ;
    command_id  : LongWord ;
    command_status :LongWord ;
    command_number:LongWord ;
end;

pSMPP_BIND = ^TSMPP_BIND ;
TSMPP_BIND = packed record
  SystemID : TSystemID ;
  Password : TPassword ;
  SystemType : TSystemType ;
  Ver        : Byte;
  Addr_TON   : Byte ;
  Addr_NPI   : Byte ;
  Addr_Range : TAddr_Range ;
end;
const
  { max short message length }
  DCS7_MAX_LEN = 160;
  DCS8_MAX_LEN = 140;
  DCSUCS2_MAX_LEN = DCS8_MAX_LEN div 2;
  { command ids }
  cmdNull   = $00000000;
  cmdBindReceiver = $00000001;
  cmdBindTransmitter = $00000002;
  cmdQuery = $00000003;
  cmdReplace = $00000007;
  cmdCancel = $00000008;
  cmdBindTransceiver = $00000009;
  cmdOutbind = $0000000B;
  cmdUnbind = $00000006;
  cmdSubmitSM = $00000004;
  cmdDeliverSM = $00000005;
  cmdEnquireLink = $00000015;
  cmdSubmitMultiply = $00000021;
  cmdAlertNotification = $00000102;
  cmdData = $00000103;
  cmdGenericNack = $80000000;
  cmdResponseBase = $80000000;
  cmdBindReceiverResponse = $80000001;
  cmdBindTransmitterResponse = $80000002;
  cmdQueryResponse = $80000003;
  cmdReplaceResponse = $80000007;
  cmdCancelResponse = $80000008;
  cmdBindTransceiverResponse = $80000009;
  cmdUnbindResponse = $80000006;
  cmdSubmitSMResponse = $80000004;
  cmdDeliverSMResponse = $80000005;
  cmdEnquireLinkResponse = $80000015;
  cmdSubmitMultiplyResponse = $80000021;
  cmdDataResponse = $80000103;
  { ESM_CLASS }
  ESM_CLASS_DELIVERY_RECEIPT = $04;
  ESM_CLASS_UDHI = $40;
implementation
end.


在我的表单上btnSendBindClick

procedure TFrmMain.btnSendBindClick(Sender: TObject);
var  hdr : TPDU_HDR ;
     bind_pkt : TSMPP_BIND ;
     mm : TMemoryStream ;
     HdrPtr : pPDU_HDR ;
     BindPtr : pSMPP_BIND ;
     sysid : AnsiString ;
     pass  : AnsiString ;
     systype : AnsiString ;
     add_rn : AnsiString ;
begin

sysid := 'sysid';
pass := 'pass';
systype := 'sys_type';
add_rn := '';

hdr.command_id := htonl(cmdBindTransceiver)  ;
hdr.command_status := htonl(cmdNull) ;
hdr.command_number  :=  htonl(cmdBindTransmitter)  ;
hdr.command_len := htonl(SizeOf(hdr)+SizeOf(bind_pkt));

bind_pkt.SystemID := pansiChar(sysid);
bind_pkt.Password := pansiChar(pass);
bind_pkt.SystemType := pansiChar(systype);
bind_pkt.Ver := 0 ;
bind_pkt.Addr_TON := 1 ;
bind_pkt.Addr_NPI := 1 ;
bind_pkt.Addr_Range := pansiChar(add_rn);

HdrPtr  := @HdrPtr ;
BindPtr := @bind_pkt ;

mm := TMemoryStream.Create ;
mm.Write(HdrPtr^,SizeOf(hdr));
mm.Position := mm.Size;
mm.Write(BindPtr^,SizeOf(bind_pkt));
mm.Position := 0 ;

clnt.Socket.SendStream(mm);

end;


我认为我需要将数据流编码为某种东西,但是我不确定。

最佳答案

我上次在1999/2000年与SMPP合作,但那时是规范。 3.4表示诸如SystemID,Password等...的字段,即声明为Var。最多nn,类型为C-OctetString。

因此,如果规范没有改变,您将完全错过它:您不能使用记录和类似的数据结构,但是必须创建一个八位字节流,其中包含无填充的ASCIIZ字符串序列,例如(使用Delphi语法):...'SystemId'#0'Password'#0'SystemType'#0...。如果我没记错的话,还应该更改整数字段的字节序。

关于delphi - 首先尝试使用SMPP协议(protocol)(绑定(bind)命令),我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/15728748/

10-11 02:16