PageRenderTime 48ms CodeModel.GetById 15ms RepoModel.GetById 0ms app.codeStats 0ms

/src/sys/dotnet/fan/sys/Depend.cs

https://bitbucket.org/bedlaczech/fan-1.0
C# | 310 lines | 240 code | 36 blank | 34 comment | 47 complexity | 976297ba2f75c061df0baab73057b4f9 MD5 | raw file
Possible License(s): CC-BY-SA-3.0
  1. //
  2. // Copyright (c) 2006, Brian Frank and Andy Frank
  3. // Licensed under the Academic Free License version 3.0
  4. //
  5. // History:
  6. // 14 Jan 06 Andy Frank Creation
  7. //
  8. using System.Collections;
  9. using System.Text;
  10. namespace Fan.Sys
  11. {
  12. /// <summary>
  13. /// Depend.
  14. /// </summary>
  15. public sealed class Depend : FanObj
  16. {
  17. //////////////////////////////////////////////////////////////////////////
  18. // Construction
  19. //////////////////////////////////////////////////////////////////////////
  20. public static Depend fromStr(string str) { return fromStr(str, true); }
  21. public static Depend fromStr(string str, bool check)
  22. {
  23. try
  24. {
  25. return new Parser(str).parse();
  26. }
  27. catch (System.Exception)
  28. {
  29. if (!check) return null;
  30. throw ParseErr.make("Depend", str).val;
  31. }
  32. }
  33. private Depend(string name, Constraint[] constraints)
  34. {
  35. this.m_name = name;
  36. this.m_constraints = constraints;
  37. }
  38. //////////////////////////////////////////////////////////////////////////
  39. // Parser
  40. //////////////////////////////////////////////////////////////////////////
  41. class Parser
  42. {
  43. internal Parser(string str)
  44. {
  45. this.m_str = str;
  46. this.m_len = str.Length;
  47. consume();
  48. }
  49. internal Depend parse()
  50. {
  51. m_name = name();
  52. constraints.Add(constraint());
  53. while (m_cur == ',')
  54. {
  55. consume();
  56. consumeSpaces();
  57. constraints.Add(constraint());
  58. }
  59. if (m_pos <= m_len) throw new System.Exception();
  60. return new Depend(m_name, (Constraint[])constraints.ToArray(
  61. System.Type.GetType("Fan.Sys.Depend+Constraint")));
  62. }
  63. private string name()
  64. {
  65. StringBuilder s = new StringBuilder();
  66. while (m_cur != ' ')
  67. {
  68. if (m_cur < 0) throw new System.Exception();
  69. s.Append((char)m_cur);
  70. consume();
  71. }
  72. consumeSpaces();
  73. if (s.Length == 0) throw new System.Exception();
  74. return s.ToString();
  75. }
  76. private Constraint constraint()
  77. {
  78. Constraint c = new Constraint();
  79. c.version = version();
  80. consumeSpaces();
  81. if (m_cur == '+')
  82. {
  83. c.isPlus = true;
  84. consume();
  85. consumeSpaces();
  86. }
  87. else if (m_cur == '-')
  88. {
  89. consume();
  90. consumeSpaces();
  91. c.endVersion = version();
  92. consumeSpaces();
  93. }
  94. return c;
  95. }
  96. private Version version()
  97. {
  98. List segs = new List(Sys.IntType, 4);
  99. int seg = consumeDigit();
  100. while (true)
  101. {
  102. if ('0' <= m_cur && m_cur <= '9')
  103. {
  104. seg = seg*10 + consumeDigit();
  105. }
  106. else
  107. {
  108. segs.add(Long.valueOf(seg));
  109. seg = 0;
  110. if (m_cur != '.') break;
  111. else consume();
  112. }
  113. }
  114. return new Version(segs);
  115. }
  116. private int consumeDigit()
  117. {
  118. if ('0' <= m_cur && m_cur <= '9')
  119. {
  120. int digit = m_cur - '0';
  121. consume();
  122. return digit;
  123. }
  124. throw new System.Exception();
  125. }
  126. private void consumeSpaces()
  127. {
  128. while(m_cur == ' ') consume();
  129. }
  130. private void consume()
  131. {
  132. if (m_pos < m_len)
  133. {
  134. m_cur = m_str[m_pos++];
  135. }
  136. else
  137. {
  138. m_cur = -1;
  139. m_pos = m_len+1;
  140. }
  141. }
  142. int m_cur;
  143. int m_pos;
  144. int m_len;
  145. string m_str;
  146. string m_name;
  147. ArrayList constraints = new ArrayList(4);
  148. }
  149. //////////////////////////////////////////////////////////////////////////
  150. // .NET
  151. //////////////////////////////////////////////////////////////////////////
  152. public override int GetHashCode()
  153. {
  154. return toStr().GetHashCode();
  155. }
  156. //////////////////////////////////////////////////////////////////////////
  157. // Identity
  158. //////////////////////////////////////////////////////////////////////////
  159. public override bool Equals(object obj)
  160. {
  161. if (obj is Depend)
  162. return toStr() == toStr(obj);
  163. else
  164. return false;
  165. }
  166. public override long hash()
  167. {
  168. return FanStr.hash(toStr());
  169. }
  170. public override Type @typeof()
  171. {
  172. return Sys.DependType;
  173. }
  174. public override string toStr()
  175. {
  176. if (m_str == null)
  177. {
  178. StringBuilder s = new StringBuilder();
  179. s.Append(m_name).Append(' ');
  180. for (int i=0; i<m_constraints.Length; i++)
  181. {
  182. if (i > 0) s.Append(',');
  183. Constraint c = m_constraints[i];
  184. s.Append(c.version);
  185. if (c.isPlus) s.Append('+');
  186. if (c.endVersion != null) s.Append('-').Append(c.endVersion);
  187. }
  188. m_str = s.ToString();
  189. }
  190. return m_str;
  191. }
  192. //////////////////////////////////////////////////////////////////////////
  193. // Methods
  194. //////////////////////////////////////////////////////////////////////////
  195. public string name()
  196. {
  197. return m_name;
  198. }
  199. public long size()
  200. {
  201. return m_constraints.Length;
  202. }
  203. public Version version() { return version(0); }
  204. public Version version(long index)
  205. {
  206. return m_constraints[(int)index].version;
  207. }
  208. public bool isPlus() { return isPlus(0); }
  209. public bool isPlus(long index)
  210. {
  211. return m_constraints[(int)index].isPlus;
  212. }
  213. public bool isRange() { return isRange(0); }
  214. public bool isRange(long index)
  215. {
  216. return m_constraints[(int)index].endVersion != null;
  217. }
  218. public Version endVersion() { return endVersion(0); }
  219. public Version endVersion(long index)
  220. {
  221. return m_constraints[(int)index].endVersion;
  222. }
  223. public bool match(Version v)
  224. {
  225. for (int i=0; i<m_constraints.Length; i++)
  226. {
  227. Constraint c = m_constraints[i];
  228. if (c.isPlus)
  229. {
  230. // versionPlus
  231. if (c.version.compare(v) <= 0)
  232. return true;
  233. }
  234. else if (c.endVersion != null)
  235. {
  236. // versionRange
  237. if (c.version.compare(v) <= 0 &&
  238. (c.endVersion.compare(v) >= 0 || match(c.endVersion, v)))
  239. return true;
  240. }
  241. else
  242. {
  243. // versionSimple
  244. if (match(c.version, v))
  245. return true;
  246. }
  247. }
  248. return false;
  249. }
  250. private static bool match(Version a, Version b)
  251. {
  252. if (a.segments().sz() > b.segments().sz()) return false;
  253. for (int i=0; i<a.segments().sz(); ++i)
  254. if (a.segment(i) != b.segment(i))
  255. return false;
  256. return true;
  257. }
  258. //////////////////////////////////////////////////////////////////////////
  259. // Constraint
  260. //////////////////////////////////////////////////////////////////////////
  261. internal class Constraint
  262. {
  263. internal Version version = null;
  264. internal bool isPlus = false;
  265. internal Version endVersion = null;
  266. }
  267. //////////////////////////////////////////////////////////////////////////
  268. // Fields
  269. //////////////////////////////////////////////////////////////////////////
  270. private readonly string m_name;
  271. private readonly Constraint[] m_constraints;
  272. private string m_str;
  273. }
  274. }