/// <summary> /// Retrieves the given bytes from the TLV table and converts them into a /// host order UInt32. /// </summary> /// <param name="tag">The TLV tag to use for retrieval</param> /// <returns>The host order result.</returns> protected UInt32?GetHostOrderUInt32FromTlv(OptionalParamCodes tag) { var data = GetOptionalParamBytes(tag); return(data == null ? new Nullable <UInt32>() : UnsignedNumConverter.SwapByteOrdering(BitConverter.ToUInt32(data, 0))); }
/// <summary> /// Takes the given value and puts it into the TLV table, accounting for /// network byte ordering. /// </summary> /// <param name="tag">The TLV tag to use for retrieval</param> /// <param name="val">The value to put into the table</param> protected void SetHostOrderValueIntoTlv(UInt16 tag, UInt32 val) { SetOptionalParamBytes( tag, BitConverter.GetBytes( UnsignedNumConverter.SwapByteOrdering(val))); }
/// <summary> /// Creates an ArrayList consisting of the Pdu header. Command ID and status /// need to be set before calling this. /// </summary> /// <returns>The Pdu as a trimmed ArrayList.</returns> protected ArrayList GetPduHeader() { ArrayList pdu = new ArrayList(); pdu.AddRange(BitConverter.GetBytes(UnsignedNumConverter.SwapByteOrdering((uint)_commandId))); pdu.AddRange(BitConverter.GetBytes(UnsignedNumConverter.SwapByteOrdering((uint)_commandStatus))); pdu.AddRange(BitConverter.GetBytes(UnsignedNumConverter.SwapByteOrdering(_sequenceNumber))); pdu.TrimToSize(); return(pdu); }
/// <summary> /// Constructor for received Pdus. /// </summary> /// <param name="incomingBytes">The incoming bytes to translate to a Pdu.</param> protected Pdu(byte[] incomingBytes) { _packetBytes = incomingBytes; _commandLength = DecodeCommandLength(_packetBytes); _commandId = DecodeCommandId(_packetBytes); _commandStatus = (CommandStatus)UnsignedNumConverter.SwapByteOrdering(BitConverter.ToUInt32(_packetBytes, 8)); _sequenceNumber = UnsignedNumConverter.SwapByteOrdering(BitConverter.ToUInt32(_packetBytes, 12)); _packetBytes = TrimResponsePdu(_packetBytes); //set the other Pdu-specific fields DecodeSmscResponse(); }
/// <summary> /// Gets the optional parameter of type T associated with /// the given tag. /// </summary> /// <param name="tag">The tag.</param> /// <returns>The optional parameter value, or null if not found</returns> public T?GetOptionalParamByte <T>(OptionalParamCodes tag) where T : struct { if (!this.ContainsOptionalParameter(tag)) { return(null); } var data = _tlvTable.GetByte(UnsignedNumConverter.SwapByteOrdering((ushort)tag)); return(typeof(T).IsEnum ? (T)Enum.ToObject(typeof(T), data) : (T)Convert.ChangeType(data, typeof(T))); }
/// <summary> /// Calculates the length of the given ArrayList representation of the Pdu and /// inserts this length into the appropriate spot in the Pdu. This will call /// TrimToSize()on the ArrayList-the caller need not do it. /// </summary> /// <param name="pdu">The protocol data unit to calculate the /// length for.</param> /// <returns>The Pdu with the length inserted, trimmed to size.</returns> protected static ArrayList InsertLengthIntoPdu(ArrayList pdu) { pdu.TrimToSize(); uint commandLength = (uint)(4 + pdu.Count); uint reqLenH2N = UnsignedNumConverter.SwapByteOrdering(commandLength); byte[] reqLenArray = BitConverter.GetBytes(reqLenH2N); //insert into the Pdu pdu.InsertRange(0, reqLenArray); pdu.TrimToSize(); return(pdu); }
/// <summary> /// Creates an ArrayList consisting of the Pdu header. Command ID and status /// need to be set before calling this. /// </summary> /// <returns>The Pdu as a trimmed ArrayList.</returns> protected ArrayList GetPduHeader() { ArrayList pdu = new ArrayList(); pdu.AddRange(BitConverter.GetBytes(UnsignedNumConverter.SwapByteOrdering((uint)_CommandID))); pdu.AddRange(BitConverter.GetBytes(UnsignedNumConverter.SwapByteOrdering(_CommandStatus))); //increase the sequence number GenerateSequenceNumber(); pdu.AddRange(BitConverter.GetBytes(UnsignedNumConverter.SwapByteOrdering(_SequenceNumber))); pdu.TrimToSize(); return(pdu); }
/// <summary> /// Sets the given TLV(as a byte array)into the table. This will not take /// care of big-endian/little-endian issues, although it will reverse the byte order /// in the tag for you(necessary for encoding). /// If the value is null, the parameter TLV will be removed instead. /// </summary> /// <param name="tag">The tag for this TLV.</param> /// <param name="val">The value of this TLV.</param> public void SetOptionalParamBytes(OptionalParamCodes tag, byte[] val) { if (val == null) { if (this.ContainsOptionalParameter(tag)) { this.RemoveOptionalParameter(tag); } } else { _tlvTable.Set(UnsignedNumConverter.SwapByteOrdering((ushort)tag), val); } }
/// <summary> /// Utility method to allow the Pdu factory to decode the command /// ID without knowing about packet structure. Some SMSCs combine /// response packets(even though they shouldn't). /// </summary> /// <param name="response">The Pdu response packet.</param> /// <returns>The ID of the Pdu command(e.g. cancel_sm_resp).</returns> public static CommandIdType DecodeCommandId(byte[] response) { uint id = 0; try { id = UnsignedNumConverter.SwapByteOrdering(BitConverter.ToUInt32(response, 4)); return((CommandIdType)id); } catch //possible that we are reading a bad command { return(CommandIdType.generic_nack); } }
/// <summary> /// Constructor for received Pdus. /// </summary> /// <param name="incomingBytes">The incoming bytes to translate to a Pdu.</param> protected Pdu(byte[] incomingBytes) { #if DEBUG Console.WriteLine("In Pdu byte[] constructor"); #endif _PacketBytes = incomingBytes; _CommandLength = DecodeCommandLength(_PacketBytes); _CommandID = DecodeCommandId(_PacketBytes); _CommandStatus = UnsignedNumConverter.SwapByteOrdering(BitConverter.ToUInt32(_PacketBytes, 8)); _SequenceNumber = UnsignedNumConverter.SwapByteOrdering(BitConverter.ToUInt32(_PacketBytes, 12)); _PacketBytes = TrimResponsePdu(_PacketBytes); //set the other Pdu-specific fields DecodeSmscResponse(); }
/// <summary> /// Sets the given TLV(as a byte) into the table. This will not take /// care of big-endian/little-endian issues, although it will reverse the byte order /// in the tag for you (necessary for encoding). /// If the value is null, the parameter TLV will be removed instead. /// </summary> /// <param name="tag">The tag for this TLV.</param> /// <param name="val">The value of this TLV.</param> /*public void SetOptionalParamByte(OptionalParamCodes tag, byte? val) * { * if (!val.HasValue) * { * if (this.ContainsOptionalParameter(tag)) * this.RemoveOptionalParameter(tag); * } * else * { * _tlvTable.Set(UnsignedNumConverter.SwapByteOrdering((ushort)tag), val.Value); * } * }*/ /// <summary> /// Sets the given TLV(as a byte) into the table. This will not take /// care of big-endian/little-endian issues, although it will reverse the byte order /// in the tag for you (necessary for encoding). /// If the value is null, the parameter TLV will be removed instead. /// </summary> /// <param name="tag">The tag for this TLV.</param> /// <param name="val">The value of this TLV.</param> public void SetOptionalParamByte <T>(OptionalParamCodes tag, T?val) where T : struct { if (!val.HasValue) { if (this.ContainsOptionalParameter(tag)) { this.RemoveOptionalParameter(tag); } } else { _tlvTable.Set(UnsignedNumConverter.SwapByteOrdering((ushort)tag), Convert.ToByte(val.Value)); } }
protected override void AppendPduData(ArrayList pdu) { pdu.AddRange(SmppStringUtil.ArrayCopyWithNull(Encoding.ASCII.GetBytes(MessageId))); pdu.Add(NumberUnsuccessful); //add the unsuccess addresses UnsuccessAddress[] unsuccessfulAddresses = UnsuccessfulAddresses; for (int i = 0; i < NumberUnsuccessful; i++) { pdu.Add((byte)unsuccessfulAddresses[i].DestinationAddressTon); pdu.Add((byte)unsuccessfulAddresses[i].DestinationAddressNpi); pdu.AddRange(SmppStringUtil.ArrayCopyWithNull( Encoding.ASCII.GetBytes(unsuccessfulAddresses[i].DestinationAddress))); pdu.AddRange(BitConverter.GetBytes( UnsignedNumConverter.SwapByteOrdering(unsuccessfulAddresses[i].ErrorStatusCode))); } }
/// <summary> /// Gets the optional parameter string associated with /// the given tag. /// </summary> /// <param name="tag">The tag in TLV.</param> /// <returns>The optional parameter string, or null if not found.</returns> public string GetOptionalParamString(OptionalParamCodes tag) { //return _tlvTable.GetOptionalParamString(UnsignedNumConverter.SwapByteOrdering(tag)); if (!this.ContainsOptionalParameter(tag)) { return(null); } var bytes = _tlvTable.GetBytes(UnsignedNumConverter.SwapByteOrdering((ushort)tag)); // Remove null termination (if found) if (bytes.Length > 0 && bytes[bytes.Length - 1] == 0x0) { Array.Resize(ref bytes, bytes.Length - 1); } return(Encoding.ASCII.GetString(bytes)); }
/// <summary> /// Takes the given value and puts it into the TLV table, accounting for /// network byte ordering. /// </summary> /// <param name="tag">The TLV tag to use for retrieval</param> /// <param name="val">The value to put into the table</param> protected void SetHostOrderValueIntoTlv(OptionalParamCodes tag, UInt32?val) { if (!val.HasValue) { if (this.ContainsOptionalParameter(tag)) { RemoveOptionalParameter(tag); } } else { if (val.Value < UInt32.MaxValue) { var msg = string.Format("Value too large for uint TLV '{0}'", tag); throw new ArgumentOutOfRangeException(msg); } SetOptionalParamBytes(tag, BitConverter.GetBytes(UnsignedNumConverter.SwapByteOrdering(val.Value))); } }
/// <summary> /// Creates the byte encoding for this Pdu. /// </summary> public override void ToMsbHexEncoding() { ArrayList pdu = GetPduHeader(); pdu.AddRange(SmppStringUtil.ArrayCopyWithNull(Encoding.ASCII.GetBytes(MessageId))); pdu.Add(NumberUnsuccessful); //add the unsuccess addresses UnsuccessAddress[] unsuccessfulAddresses = UnsuccessfulAddresses; for (int i = 0; i < NumberUnsuccessful; i++) { pdu.Add((byte)unsuccessfulAddresses[i].DestinationAddressTon); pdu.Add((byte)unsuccessfulAddresses[i].DestinationAddressNpi); pdu.AddRange(SmppStringUtil.ArrayCopyWithNull( Encoding.ASCII.GetBytes(unsuccessfulAddresses[i].DestinationAddress))); pdu.AddRange(BitConverter.GetBytes( UnsignedNumConverter.SwapByteOrdering(unsuccessfulAddresses[i].ErrorStatusCode))); } // PacketBytes = EncodePduForTransmission(pdu); }
/// <summary> /// Sets the given TLV(as a string)into the table. /// This will reverse the byte order in the tag for you (necessary for encoding). /// If the value is null, the parameter TLV will be removed instead. /// </summary> /// <param name="tag">The tag for this TLV.</param> /// <param name="val">The value of this TLV.</param> public void SetOptionalParamString(OptionalParamCodes tag, string val, bool nullTerminated) { if (val == null) { if (this.ContainsOptionalParameter(tag)) { this.RemoveOptionalParameter(tag); } } else { var bytes = Encoding.ASCII.GetBytes(val); // Add a null byte to the end if needed. if (nullTerminated) { Array.Resize(ref bytes, bytes.Length + 1); } _tlvTable.Set(UnsignedNumConverter.SwapByteOrdering((ushort)tag), bytes); } }
/// <summary> /// Gets the optional parameter bytes associated with /// the given tag. /// </summary> /// <param name="tag">The tag in TLV.</param> /// <returns>The optional parameter bytes, null if /// not found.</returns> public byte[] GetOptionalParamBytes(UInt16 tag) { return(_tlvTable.GetOptionalParamBytes(UnsignedNumConverter.SwapByteOrdering(tag))); }
/// <summary> /// Determines whether [contains optional parameter] [specified by tag]. /// </summary> /// <param name="tag">The tag.</param> /// <returns> /// <c>true</c> if [contains optional parameter] [specified by tag]; otherwise, <c>false</c>. /// </returns> public bool ContainsOptionalParameter(OptionalParamCodes tag) { return(_tlvTable.ContainsKey(UnsignedNumConverter.SwapByteOrdering((ushort)tag))); }
/// <summary> /// Gets the optional parameter bytes associated with /// the given tag. /// </summary> /// <param name="tag">The tag in TLV.</param> /// <returns>The optional parameter bytes, or null if not found</returns> public byte[] GetOptionalParamBytes(OptionalParamCodes tag) { //return _tlvTable.GetOptionalParamBytes(UnsignedNumConverter.SwapByteOrdering(tag)); return(this.ContainsOptionalParameter(tag) ? _tlvTable.GetBytes(UnsignedNumConverter.SwapByteOrdering((ushort)tag)) : null); }
/// <summary> /// Retrieves the given bytes from the TLV table and converts them into a /// host order UInt32. /// </summary> /// <param name="tag">The TLV tag to use for retrieval</param> /// <returns>The host order result.</returns> protected UInt32 GetHostOrderUInt32FromTlv(ushort tag) { return(UnsignedNumConverter.SwapByteOrdering( BitConverter.ToUInt32(GetOptionalParamBytes(tag), 0))); }
/// <summary> /// Sets the given TLV(as a byte array)into the table. This will not take /// care of big-endian/little-endian issues, although it will reverse the byte order /// in the tag for you(necessary for encoding). This ignores null values. /// </summary> /// <param name="tag">The tag for this TLV.</param> /// <param name="val">The value of this TLV.</param> public void SetOptionalParamBytes(UInt16 tag, byte[] val) { _tlvTable.SetOptionalParamBytes(UnsignedNumConverter.SwapByteOrdering(tag), val); }
/// <summary> /// Utility method to allow the Pdu factory to decode the command /// length without knowing about packet structure. Some SMSCs combine /// response packets(even though they shouldn't). /// </summary> /// <param name="response">The Pdu response packet.</param> /// <returns>The length of the Pdu command.</returns> public static UInt32 DecodeCommandLength(byte[] response) { return(UnsignedNumConverter.SwapByteOrdering(BitConverter.ToUInt32(response, 0))); }
/// <summary> /// Allows the updating of TLV values. This will reverse the byte order in the tag for you ///(necessary for encoding). /// </summary> /// <param name="tag">The tag for this TLV.</param> /// <param name="val">The value of this TLV.</param> public void UpdateOptionalParamString(UInt16 tag, string val) { _tlvTable.UpdateOptionalParamString(UnsignedNumConverter.SwapByteOrdering(tag), val); }
/// <summary> /// Removes the optional parameter. /// </summary> /// <param name="tag">The tag.</param> public void RemoveOptionalParameter(OptionalParamCodes tag) { _tlvTable.Remove(UnsignedNumConverter.SwapByteOrdering((ushort)tag)); }