PeerInfo.vala 2.9 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788
  1. using GLib;
  2. using Gee;
  3. using LibPeer.Util;
  4. namespace LibPeer.Networks
  5. {
  6. public abstract class PeerInfo : Object {
  7. private static ConcurrentHashMap<Bytes, Type> info_types = new ConcurrentHashMap<Bytes, Type>((a) => a.hash(), (a, b) => a.compare(b) == 0);
  8. protected abstract void build(uint8 data_length, InputStream stream, Bytes network_type) throws IOError, Error;
  9. public abstract Bytes get_network_identifier();
  10. protected abstract Bytes get_data_segment();
  11. public abstract string to_string();
  12. public abstract bool equals(PeerInfo other);
  13. public abstract uint hash();
  14. public void serialise(OutputStream stream) throws IOError, Error {
  15. // Create a stream writer
  16. var writer = StreamUtil.get_data_output_stream(stream);
  17. // print("Start serialising PeerInfo\n");
  18. // Get the informational data
  19. var type = get_network_identifier();
  20. var data = get_data_segment();
  21. // print("Serialising type length\n");
  22. // Write the length of the network type
  23. writer.put_byte((uint8)type.length);
  24. // print("Serialising data segment length\n");
  25. // Write the length of the data segment
  26. writer.put_byte((uint8)data.length);
  27. var stringType = new ByteComposer().add_bytes(type).to_string(true);
  28. // print(@"Serialising type: $(stringType) ($(to_string()))\n");
  29. // Write the network identifier
  30. writer.write_bytes(type);
  31. // print("Serialising data\n");
  32. // Write the data
  33. writer.write_bytes(data);
  34. // print("Serialised peer info\n");
  35. writer.flush();
  36. }
  37. public static PeerInfo deserialise(InputStream stream) throws IOError, Error {
  38. // Create a data input stream
  39. var reader = StreamUtil.get_data_input_stream(stream);
  40. // Get the length of the network type
  41. var type_length = reader.read_byte();
  42. // Get the length of the data segment
  43. var data_length = reader.read_byte();
  44. // Read the network type
  45. var network_type = reader.read_bytes(type_length);
  46. // Get the info subclass
  47. Type peer_info_type = typeof(UnknownPeerInfo);
  48. if(info_types.has_key(network_type)) {
  49. peer_info_type = info_types.get(network_type);
  50. }
  51. // Create the peer info object
  52. PeerInfo peer_info = Object.new(peer_info_type) as PeerInfo;
  53. // Build out the data
  54. peer_info.build(data_length, reader, network_type);
  55. // Return the object
  56. return peer_info;
  57. }
  58. protected void register_info_type() {
  59. info_types.set(get_network_identifier(), get_type());
  60. }
  61. }
  62. }