* Makefile ($(build_lib)): Make CYCLIC_DEP_FILES depend on this.
[mono.git] / mcs / class / Microsoft.Build.Engine / Microsoft.Build.BuildEngine / MetadataReference.cs
index 41ba8f32bb8d62db4217c70f7ea09a061fdf1848..3e245ab1c9deca3ad1b59b117c4690a60936a98b 100644 (file)
 #if NET_2_0
 
 using System;
+using System.Collections.Generic;
+using System.Text;
 using Microsoft.Build.Framework;
 using Microsoft.Build.Utilities;
 
 namespace Microsoft.Build.BuildEngine {
-       internal class MetadataReference {
+       internal class MetadataReference : IReference {
        
                string          itemName;
                string          metadataName;
+               int start;
+               int length;
        
-               public MetadataReference ()
-               {
-               }
-
-               public MetadataReference (string itemName, string metadataName)
+               public MetadataReference (string itemName, string metadataName, int start, int length)
                {
                        this.itemName = itemName;
                        this.metadataName = metadataName;
-               }
-               
-               public void ParseSource (string source)
-               {
-                       string sourceWithoutParens;
-                       int dot;
-               
-                       if (source.Length < 4)
-                               throw new ArgumentException ("source is too short.");
-                       
-                       sourceWithoutParens = source.Substring (2, source.Length - 3);
-                       dot = sourceWithoutParens.IndexOf ('.');
-                       
-                       if (dot != -1) {
-                               itemName = sourceWithoutParens.Substring (0, dot);
-                               metadataName = sourceWithoutParens.Substring (dot + 1, sourceWithoutParens.Length - dot - 1); 
-                       } else {
-                               metadataName = sourceWithoutParens;
-                       }
+                       this.start = start;
+                       this.length = length;
                }
                
                public string ItemName {
@@ -77,7 +60,75 @@ namespace Microsoft.Build.BuildEngine {
                public bool IsQualified {
                        get { return (itemName == null) ? false : true; }
                }
+
+               public int Start {
+                       get { return start; }
+               }
+
+               public int End {
+                       get { return start + length - 1; }
+               }
+
+               public string ConvertToString (Project project)
+               {
+                       return project.GetMetadataBatched (itemName, metadataName);
+               }
+
+               public ITaskItem [] ConvertToITaskItemArray (Project project)
+               {
+                       List<ITaskItem> items = new List<ITaskItem> ();
+                       if (IsQualified) {
+                               // Bucket would have item lists with same metadata values,
+                               // so just get the value from the first item
+                               BuildItemGroup group;
+                               if (project.TryGetEvaluatedItemByNameBatched (itemName, out group))
+                                       BuildItemGroupToITaskItems (group, items, true);
+                       } else {
+                               // Get unique metadata values from _all_ item lists
+                               foreach (BuildItemGroup group in project.GetAllItemGroups ())
+                                       BuildItemGroupToITaskItems (group, items, false);
+                       }
+
+                       return items.Count == 0 ? null : items.ToArray ();
+               }
+
+               // Gets metadata values from build item @group and adds as ITaskItem
+               // objects to @items
+               // @only_one: Batched case, all item lists would have same metadata values,
+               //            just return first one
+               void BuildItemGroupToITaskItems (BuildItemGroup group, List<ITaskItem> items, bool only_one)
+               {
+                       foreach (BuildItem item in group) {
+                               if (!item.HasMetadata (metadataName))
+                                       continue;
+
+                               string metadata = item.GetMetadata (metadataName);
+                               if (HasTaskItem (items, metadata))
+                                       //return only unique metadata values
+                                       continue;
+
+                               items.Add (new TaskItem (metadata));
+                               if (only_one)
+                                       break;
+                       }
+               }
+
+               private bool HasTaskItem (List<ITaskItem> items, string itemspec)
+               {
+                       foreach (ITaskItem task_item in items)
+                               if (task_item.ItemSpec == itemspec)
+                                       return true;
+                       return false;
+               }
+
+               public override string ToString ()
+               {
+                       if (IsQualified)
+                               return String.Format ("%({0}.{1})", itemName, metadataName);
+                       else
+                               return String.Format ("%({0})", metadataName);
+               }
        }
 }
 
-#endif
\ No newline at end of file
+#endif