1 // Written in the D programming language.
2 
3 /**
4 A type for representing the nwqid object of the 9P / Styx protocol. 
5 
6 Copyright: LightHouse Software, 2021
7 License:   $(HTTP https://github.com/aquaratixc/ESL-License, Experimental Software License 1.0).
8 Authors:   Oleg Bakharev,
9 		   Ilya Pertsev
10 */
11 module styx2000.protobj.nwqid;
12 
13 private {
14 	import std.conv : to;
15 	import std.string : format;
16 	
17 	import styx2000.lowlevel.endianness;
18 	
19 	import styx2000.protobj.styxobject;
20 }
21 
22 public {
23 	import styx2000.protobj.qid;
24 }
25 
26 /**
27 	A class that provides a type for the Nwqid field in some Styx messages. Inherits methods from the StyxObject class. 
28 	See_Also:
29 		https://web.archive.org/web/20201029184954/https://powerman.name/Inferno/man/5/0intro.html
30 */
31 class Nwqid : StyxObject
32 {
33 	protected {
34 		Qid[] _nwqid;
35 		
36 		ubyte[] _representation;
37 	}
38 	
39 	private {
40 		// update qids list
41 		void updateQids()
42 		{
43 			if (_nwqid.length == 0)
44 			{
45 				_representation = [0, 0];
46 			}
47 			else
48 			{
49 				_representation = toLEBytes!ushort(
50 					cast(ushort) _nwqid.length
51 				);
52 				foreach (e; _nwqid)
53 				{
54 					_representation ~= e.pack;
55 				}
56 			}
57 		}
58 	}
59 	
60 	/**
61 	A constructor that creates an object of the Nwqid class with the given parameter in the form of qid's array. 
62 	If called without parameters, then the default parameter is empty qid's array. 
63     Params:
64     nwname = Full file path as qid's array.
65     
66     Typical usage:
67     ----
68     Nwqid nwqid = new Nwqid([new Qid, new Qid]);
69     ----
70     */
71 	this(Qid[] nwqid = [])
72 	{
73 		_nwqid = nwqid;
74 		_representation = [];
75 		updateQids;
76 	}
77 	
78 	/// Get all qids in path as qid's array
79 	Qid[] getQid()
80 	{
81 		return _nwqid;
82 	}
83 	
84 	/// Number of qids
85 	ushort countOfQids()
86 	{
87 		return fromLEBytes!ushort(_representation[0..2]);
88 	}
89 	
90 	/// Set all qids in path as qid's array
91 	void setQid(Qid[] nwqid...)
92 	{
93 		_nwqid = nwqid;
94 		_representation = [];
95 		updateQids;
96 	}
97 	
98 	/// Convenient aliases for uniformity
99 	alias setNwqid = setQid;
100 	alias getNwqid = getQid;
101 	
102 	/// Another aliases
103 	alias setQids = setQid;
104 	alias getQids = getQid;
105 	
106 	/// Pack to bytes array
107 	ubyte[] pack()
108 	{
109 		return _representation;
110 	}
111 	
112 	/// Unpack from bytes array
113 	void unpack(ubyte[] bytes...)
114 	{
115 		_representation = bytes;
116 		_nwqid = [];
117 		ushort length = fromLEBytes!ushort(bytes[0..2]);
118 		auto vlsPosition = 2;
119 		
120 		foreach (_; 0..length)
121 		{
122 			Qid qid = new Qid;
123 			qid.unpack(bytes[vlsPosition..$]);
124 			_nwqid ~= qid;
125 			vlsPosition += 13;
126 		}
127 	}
128 	
129 	/// Convenient string representation of an object for printing
130 	override string toString()
131 	{
132 		return format(
133 			`Nwqid(nwqid=%d, wqid=%s)`,
134 			fromLEBytes!ushort(_representation[0..2]),
135 			_nwqid.to!string
136 		);
137 	}
138 	
139 	/// An alias for easier packing into a byte array without having to manually call the pack() method
140 	alias pack this;
141 }