Skip to content
This repository
Newer
Older
100644 226 lines (175 sloc) 6.224 kb
3d12b890 »
2012-04-08 Implement a basic mechanism for assigning each unique method signatur…
1 using System;
2 using System.Collections.Generic;
db2bb4d4 »
2012-04-10 Track distinct overloads of a method separately from redefinitions of…
3 using System.Linq;
3d12b890 »
2012-04-08 Implement a basic mechanism for assigning each unique method signatur…
4 using System.Threading;
5 using Mono.Cecil;
6
7 namespace JSIL.Internal {
8 public class MethodSignature {
db2bb4d4 »
2012-04-10 Track distinct overloads of a method separately from redefinitions of…
9 public class EqualityComparer : IEqualityComparer<MethodSignature> {
10 public bool Equals (MethodSignature x, MethodSignature y) {
11 if (x == null)
12 return x == y;
13
14 return x.Equals(y);
15 }
16
17 public int GetHashCode (MethodSignature obj) {
18 return obj.GetHashCode();
19 }
20 }
21
3d12b890 »
2012-04-08 Implement a basic mechanism for assigning each unique method signatur…
22 public readonly TypeReference ReturnType;
23 public readonly TypeReference[] ParameterTypes;
24 public readonly string[] GenericParameterNames;
25
f7122579 »
2012-04-10 Improve MethodSignature HashCodes so they vary more.
26 internal int? ID;
27
db2bb4d4 »
2012-04-10 Track distinct overloads of a method separately from redefinitions of…
28 protected int? _Hash;
29
3d12b890 »
2012-04-08 Implement a basic mechanism for assigning each unique method signatur…
30 public MethodSignature (
31 TypeReference returnType, TypeReference[] parameterTypes, string[] genericParameterNames
32 ) {
33 ReturnType = returnType;
34 ParameterTypes = parameterTypes;
35 GenericParameterNames = genericParameterNames;
36 }
db2bb4d4 »
2012-04-10 Track distinct overloads of a method separately from redefinitions of…
37
38 public int ParameterCount {
39 get {
40 if (ParameterTypes == null)
41 return 0;
42
43 return ParameterTypes.Length;
44 }
45 }
46
47 public int GenericParameterCount {
48 get {
49 if (GenericParameterNames == null)
50 return 0;
51
52 return GenericParameterNames.Length;
53 }
54 }
55
56 public bool Equals (MethodSignature rhs) {
57 if (this == rhs)
58 return true;
59
60 if (!ILBlockTranslator.TypesAreEqual(ReturnType, rhs.ReturnType, true))
61 return false;
62
63 if (GenericParameterCount != rhs.GenericParameterCount)
64 return false;
65
66 if (ParameterCount != rhs.ParameterCount)
67 return false;
68
69 for (int i = 0, c = ParameterCount; i < c; i++) {
70 if (!ILBlockTranslator.TypesAreEqual(ParameterTypes[i], rhs.ParameterTypes[i], true))
71 return false;
72 }
73
74 return true;
75 }
76
77 public override bool Equals (object obj) {
78 var ms = obj as MethodSignature;
79
80 if (ms != null)
81 return Equals(ms);
82 else
83 return base.Equals(obj);
84 }
85
86 public override int GetHashCode () {
87 if (_Hash.HasValue)
88 return _Hash.Value;
89
f7122579 »
2012-04-10 Improve MethodSignature HashCodes so they vary more.
90 int hash = 0;
91
92 if ((ReturnType != null) && !ILBlockTranslator.IsOpenType(ReturnType))
93 hash = ReturnType.Name.GetHashCode();
94
95 if ((ParameterCount > 0) && !ILBlockTranslator.IsOpenType(ParameterTypes[0]))
96 hash ^= (ParameterTypes[0].Name.GetHashCode() << 16);
db2bb4d4 »
2012-04-10 Track distinct overloads of a method separately from redefinitions of…
97
f7122579 »
2012-04-10 Improve MethodSignature HashCodes so they vary more.
98 hash ^= (GenericParameterCount) << 24;
99
100 hash ^= (ParameterCount) << 28;
db2bb4d4 »
2012-04-10 Track distinct overloads of a method separately from redefinitions of…
101
102 _Hash = hash;
103 return hash;
104 }
3d12b890 »
2012-04-08 Implement a basic mechanism for assigning each unique method signatur…
105 }
106
107 public class MethodSignatureCache {
f7122579 »
2012-04-10 Improve MethodSignature HashCodes so they vary more.
108 // private readonly ConcurrentCache<MethodSignature, int> IDs;
109 private int NextID = 0;
3d12b890 »
2012-04-08 Implement a basic mechanism for assigning each unique method signatur…
110
f7122579 »
2012-04-10 Improve MethodSignature HashCodes so they vary more.
111 public MethodSignatureCache () {
112 /*
113 IDs = new ConcurrentCache<MethodSignature, int>(
114 Environment.ProcessorCount, 8192, new MethodSignature.EqualityComparer()
115 );
116 */
117 }
3d12b890 »
2012-04-08 Implement a basic mechanism for assigning each unique method signatur…
118
f7122579 »
2012-04-10 Improve MethodSignature HashCodes so they vary more.
119 private int CreateEntry (MethodSignature signature) {
120 var id = Interlocked.Increment(ref NextID);
121 signature.ID = id;
122 return id;
3d12b890 »
2012-04-08 Implement a basic mechanism for assigning each unique method signatur…
123 }
124
f7122579 »
2012-04-10 Improve MethodSignature HashCodes so they vary more.
125 public bool AssignID (MethodSignature signature) {
126 /*
127 return IDs.TryCreate(
128 signature, () => CreateEntry(signature)
129 );
130 */
3d12b890 »
2012-04-08 Implement a basic mechanism for assigning each unique method signatur…
131
f7122579 »
2012-04-10 Improve MethodSignature HashCodes so they vary more.
132 CreateEntry(signature);
133
134 return true;
3d12b890 »
2012-04-08 Implement a basic mechanism for assigning each unique method signatur…
135 }
136
137 public int Get (MethodSignature signature) {
f7122579 »
2012-04-10 Improve MethodSignature HashCodes so they vary more.
138 if (signature.ID.HasValue)
139 return signature.ID.Value;
140
141 if (AssignID(signature))
142 return signature.ID.Value;
143 else
27295578 »
2012-04-15 Improve various error messages to be clearer and contain more informa…
144 throw new InvalidOperationException("Signature ID assignment failed");
3d12b890 »
2012-04-08 Implement a basic mechanism for assigning each unique method signatur…
145
f7122579 »
2012-04-10 Improve MethodSignature HashCodes so they vary more.
146 /*
3d12b890 »
2012-04-08 Implement a basic mechanism for assigning each unique method signatur…
147 return IDs.GetOrCreate(
f7122579 »
2012-04-10 Improve MethodSignature HashCodes so they vary more.
148 signature, () => CreateEntry(signature)
3d12b890 »
2012-04-08 Implement a basic mechanism for assigning each unique method signatur…
149 );
f7122579 »
2012-04-10 Improve MethodSignature HashCodes so they vary more.
150 */
3d12b890 »
2012-04-08 Implement a basic mechanism for assigning each unique method signatur…
151 }
152 }
db2bb4d4 »
2012-04-10 Track distinct overloads of a method separately from redefinitions of…
153
154 public class MethodSignatureSet {
155 private class Count {
156 public int Value = 0;
157 }
158
159 private int _Count = 0;
160 private readonly ConcurrentCache<MethodSignature, Count> Counts;
161
162 public MethodSignatureSet () {
163 Counts = new ConcurrentCache<MethodSignature, Count>(
f7122579 »
2012-04-10 Improve MethodSignature HashCodes so they vary more.
164 1, 8, new MethodSignature.EqualityComparer()
db2bb4d4 »
2012-04-10 Track distinct overloads of a method separately from redefinitions of…
165 );
166 }
167
184f0449 »
2012-04-11 Mannux sample works again.
168 public IEnumerable<MethodSignature> Signatures {
169 get {
170 return Counts.Keys;
171 }
172 }
173
db2bb4d4 »
2012-04-10 Track distinct overloads of a method separately from redefinitions of…
174 public void Add (MethodSignature signature) {
175 var count = Counts.GetOrCreate(
176 signature, () => new Count()
177 );
178
179 Interlocked.Increment(ref _Count);
180 Interlocked.Increment(ref count.Value);
181 }
182
183 public int GetCountOf (MethodSignature signature) {
184 Count result;
185 if (Counts.TryGet(signature, out result))
186 return result.Value;
187
188 return 0;
189 }
190
191 public int DefinitionCount {
192 get {
193 return _Count;
194 }
195 }
196
197 public int DistinctSignatureCount {
198 get {
199 return Counts.Count;
200 }
201 }
202 }
203
204 public class MethodSignatureCollection : ConcurrentCache<string, MethodSignatureSet> {
205 public MethodSignatureCollection ()
206 : base() {
207 }
208
209 public int GetOverloadCountOf (string methodName) {
210 MethodSignatureSet set;
211 if (TryGet(methodName, out set))
212 return set.DistinctSignatureCount;
213
214 return 0;
215 }
216
217 public int GetDefinitionCountOf (MethodInfo method) {
218 MethodSignatureSet set;
219 if (TryGet(method.Name, out set))
220 return set.GetCountOf(method.Signature);
221
222 return 0;
223 }
224 }
3d12b890 »
2012-04-08 Implement a basic mechanism for assigning each unique method signatur…
225 }
Something went wrong with that request. Please try again.