Mercurial > pub > bltoolkit
comparison Source/Reflection/Emit/AssemblyBuilderHelper.cs @ 0:f990fcb411a9
Копия текущей версии из github
author | cin |
---|---|
date | Thu, 27 Mar 2014 21:46:09 +0400 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
-1:000000000000 | 0:f990fcb411a9 |
---|---|
1 using System; | |
2 using System.Configuration.Assemblies; | |
3 using System.Reflection; | |
4 using System.Reflection.Emit; | |
5 using System.Security; | |
6 using System.Threading; | |
7 | |
8 namespace BLToolkit.Reflection.Emit | |
9 { | |
10 /// <summary> | |
11 /// A wrapper around the <see cref="AssemblyBuilder"/> and <see cref="ModuleBuilder"/> classes. | |
12 /// </summary> | |
13 /// <include file="Examples.CS.xml" path='examples/emit[@name="Emit"]/*' /> | |
14 /// <include file="Examples.VB.xml" path='examples/emit[@name="Emit"]/*' /> | |
15 /// <seealso cref="System.Reflection.Emit.AssemblyBuilder">AssemblyBuilder Class</seealso> | |
16 /// <seealso cref="System.Reflection.Emit.ModuleBuilder">ModuleBuilder Class</seealso> | |
17 public class AssemblyBuilderHelper | |
18 { | |
19 /// <summary> | |
20 /// Initializes a new instance of the <see cref="AssemblyBuilderHelper"/> class | |
21 /// with the specified parameters. | |
22 /// </summary> | |
23 /// <param name="path">The path where the assembly will be saved.</param> | |
24 public AssemblyBuilderHelper(string path) : this(path, null, null) | |
25 { | |
26 } | |
27 | |
28 /// <summary> | |
29 /// Initializes a new instance of the <see cref="AssemblyBuilderHelper"/> class | |
30 /// with the specified parameters. | |
31 /// </summary> | |
32 /// <param name="path">The path where the assembly will be saved.</param> | |
33 /// <param name="version">The assembly version.</param> | |
34 /// <param name="keyFile">The key pair file to sign the assembly.</param> | |
35 public AssemblyBuilderHelper(string path, Version version, string keyFile) | |
36 { | |
37 if (path == null) throw new ArgumentNullException("path"); | |
38 | |
39 var idx = path.IndexOf(','); | |
40 | |
41 if (idx > 0) | |
42 { | |
43 path = path.Substring(0, idx); | |
44 | |
45 if (path.Length >= 200) | |
46 { | |
47 idx = path.IndexOf('`'); | |
48 | |
49 if (idx > 0) | |
50 { | |
51 var idx2 = path.LastIndexOf('.'); | |
52 | |
53 if (idx2 > 0 && idx2 > idx) | |
54 path = path.Substring(0, idx + 1) + path.Substring(idx2 + 1); | |
55 } | |
56 } | |
57 } | |
58 | |
59 path = path.Replace("+", ".").Replace("<", "_").Replace(">", "_"); | |
60 | |
61 if (path.Length >= 260) | |
62 { | |
63 path = path.Substring(0, 248); | |
64 | |
65 for (var i = 0; i < int.MaxValue; i++) | |
66 { | |
67 var newPath = string.Format("{0}_{1:0000}.dll", path, i); | |
68 | |
69 if (!System.IO.File.Exists(newPath)) | |
70 { | |
71 path = newPath; | |
72 break; | |
73 } | |
74 } | |
75 } | |
76 | |
77 var assemblyName = System.IO.Path.GetFileNameWithoutExtension(path); | |
78 var assemblyDir = System.IO.Path.GetDirectoryName(path); | |
79 | |
80 Path = path; | |
81 _assemblyName.Name = assemblyName; | |
82 | |
83 if (version != null) | |
84 _assemblyName.Version = version; | |
85 | |
86 #if !SILVERLIGHT | |
87 | |
88 if (!string.IsNullOrEmpty(keyFile)) | |
89 { | |
90 _assemblyName.Flags |= AssemblyNameFlags.PublicKey; | |
91 _assemblyName.KeyPair = new StrongNameKeyPair(System.IO.File.OpenRead(keyFile)); | |
92 _assemblyName.HashAlgorithm = AssemblyHashAlgorithm.SHA1; | |
93 } | |
94 | |
95 #endif | |
96 | |
97 #if DEBUG | |
98 _assemblyName.Flags |= AssemblyNameFlags.EnableJITcompileTracking; | |
99 #else | |
100 _assemblyName.Flags |= AssemblyNameFlags.EnableJITcompileOptimizer; | |
101 #endif | |
102 | |
103 _createAssemblyBuilder = _ => | |
104 { | |
105 #if SILVERLIGHT | |
106 _assemblyBuilder = Thread.GetDomain().DefineDynamicAssembly(_assemblyName, AssemblyBuilderAccess.Run); | |
107 #else | |
108 _assemblyBuilder = | |
109 string.IsNullOrEmpty(assemblyDir)? | |
110 Thread.GetDomain().DefineDynamicAssembly(_assemblyName, AssemblyBuilderAccess.RunAndSave): | |
111 Thread.GetDomain().DefineDynamicAssembly(_assemblyName, AssemblyBuilderAccess.RunAndSave, assemblyDir); | |
112 #endif | |
113 | |
114 _assemblyBuilder.SetCustomAttribute(BLToolkitAttribute); | |
115 | |
116 #if !SILVERLIGHT | |
117 | |
118 _assemblyBuilder.SetCustomAttribute( | |
119 new CustomAttributeBuilder( | |
120 typeof(AllowPartiallyTrustedCallersAttribute) | |
121 .GetConstructor(Type.EmptyTypes), | |
122 new object[0])); | |
123 | |
124 #endif | |
125 }; | |
126 } | |
127 | |
128 /// <summary> | |
129 /// Gets the path where the assembly will be saved. | |
130 /// </summary> | |
131 public string Path { get; private set; } | |
132 | |
133 private readonly AssemblyName _assemblyName = new AssemblyName(); | |
134 /// <summary> | |
135 /// Gets AssemblyName. | |
136 /// </summary> | |
137 public AssemblyName AssemblyName | |
138 { | |
139 get { return _assemblyName; } | |
140 } | |
141 | |
142 readonly Action<int> _createAssemblyBuilder; | |
143 | |
144 AssemblyBuilder _assemblyBuilder; | |
145 /// <summary> | |
146 /// Gets AssemblyBuilder. | |
147 /// </summary> | |
148 public AssemblyBuilder AssemblyBuilder | |
149 { | |
150 get | |
151 { | |
152 if (_assemblyBuilder == null) | |
153 _createAssemblyBuilder(0); | |
154 return _assemblyBuilder; | |
155 } | |
156 } | |
157 | |
158 /// <summary> | |
159 /// Gets the path where the assembly will be saved. | |
160 /// </summary> | |
161 public string ModulePath | |
162 { | |
163 get { return System.IO.Path.GetFileName(Path); } | |
164 } | |
165 | |
166 private ModuleBuilder _moduleBuilder; | |
167 /// <summary> | |
168 /// Gets ModuleBuilder. | |
169 /// </summary> | |
170 public ModuleBuilder ModuleBuilder | |
171 { | |
172 get | |
173 { | |
174 if (_moduleBuilder == null) | |
175 { | |
176 _moduleBuilder = AssemblyBuilder.DefineDynamicModule(ModulePath); | |
177 _moduleBuilder.SetCustomAttribute(BLToolkitAttribute); | |
178 | |
179 } | |
180 | |
181 return _moduleBuilder; | |
182 } | |
183 } | |
184 | |
185 private CustomAttributeBuilder _blToolkitAttribute; | |
186 /// <summary> | |
187 /// Retrieves a cached instance of <see cref="BLToolkit.TypeBuilder.BLToolkitGeneratedAttribute"/> builder. | |
188 /// </summary> | |
189 public CustomAttributeBuilder BLToolkitAttribute | |
190 { | |
191 get | |
192 { | |
193 if (_blToolkitAttribute == null) | |
194 { | |
195 var at = typeof(TypeBuilder.BLToolkitGeneratedAttribute); | |
196 var ci = at.GetConstructor(Type.EmptyTypes); | |
197 | |
198 _blToolkitAttribute = new CustomAttributeBuilder(ci, new object[0]); | |
199 } | |
200 | |
201 return _blToolkitAttribute; | |
202 } | |
203 } | |
204 | |
205 /// <summary> | |
206 /// Converts the supplied <see cref="AssemblyBuilderHelper"/> to a <see cref="AssemblyBuilder"/>. | |
207 /// </summary> | |
208 /// <param name="assemblyBuilder">The <see cref="AssemblyBuilderHelper"/>.</param> | |
209 /// <returns>An <see cref="AssemblyBuilder"/>.</returns> | |
210 public static implicit operator AssemblyBuilder(AssemblyBuilderHelper assemblyBuilder) | |
211 { | |
212 if (assemblyBuilder == null) throw new ArgumentNullException("assemblyBuilder"); | |
213 | |
214 return assemblyBuilder.AssemblyBuilder; | |
215 } | |
216 | |
217 /// <summary> | |
218 /// Converts the supplied <see cref="AssemblyBuilderHelper"/> to a <see cref="ModuleBuilder"/>. | |
219 /// </summary> | |
220 /// <param name="assemblyBuilder">The <see cref="AssemblyBuilderHelper"/>.</param> | |
221 /// <returns>A <see cref="ModuleBuilder"/>.</returns> | |
222 public static implicit operator ModuleBuilder(AssemblyBuilderHelper assemblyBuilder) | |
223 { | |
224 if (assemblyBuilder == null) throw new ArgumentNullException("assemblyBuilder"); | |
225 | |
226 return assemblyBuilder.ModuleBuilder; | |
227 } | |
228 | |
229 /// <summary> | |
230 /// Saves this dynamic assembly to disk. | |
231 /// </summary> | |
232 public void Save() | |
233 { | |
234 #if !SILVERLIGHT | |
235 | |
236 if (_assemblyBuilder != null) | |
237 _assemblyBuilder.Save(ModulePath); | |
238 | |
239 #endif | |
240 } | |
241 | |
242 #region DefineType Overrides | |
243 | |
244 /// <summary> | |
245 /// Constructs a <see cref="TypeBuilderHelper"/> for a type with the specified name. | |
246 /// </summary> | |
247 /// <param name="name">The full path of the type.</param> | |
248 /// <returns>Returns the created <see cref="TypeBuilderHelper"/>.</returns> | |
249 /// <seealso cref="System.Reflection.Emit.ModuleBuilder.DefineType(string)">ModuleBuilder.DefineType Method</seealso> | |
250 public TypeBuilderHelper DefineType(string name) | |
251 { | |
252 return new TypeBuilderHelper(this, ModuleBuilder.DefineType(name)); | |
253 } | |
254 | |
255 /// <summary> | |
256 /// Constructs a <see cref="TypeBuilderHelper"/> for a type with the specified name and base type. | |
257 /// </summary> | |
258 /// <param name="name">The full path of the type.</param> | |
259 /// <param name="parent">The Type that the defined type extends.</param> | |
260 /// <returns>Returns the created <see cref="TypeBuilderHelper"/>.</returns> | |
261 /// <seealso cref="System.Reflection.Emit.ModuleBuilder.DefineType(string,TypeAttributes,Type)">ModuleBuilder.DefineType Method</seealso> | |
262 public TypeBuilderHelper DefineType(string name, Type parent) | |
263 { | |
264 return new TypeBuilderHelper(this, ModuleBuilder.DefineType(name, TypeAttributes.Public, parent)); | |
265 } | |
266 | |
267 /// <summary> | |
268 /// Constructs a <see cref="TypeBuilderHelper"/> for a type with the specified name, its attributes, and base type. | |
269 /// </summary> | |
270 /// <param name="name">The full path of the type.</param> | |
271 /// <param name="attrs">The attribute to be associated with the type.</param> | |
272 /// <param name="parent">The Type that the defined type extends.</param> | |
273 /// <returns>Returns the created <see cref="TypeBuilderHelper"/>.</returns> | |
274 /// <seealso cref="System.Reflection.Emit.ModuleBuilder.DefineType(string,TypeAttributes,Type)">ModuleBuilder.DefineType Method</seealso> | |
275 public TypeBuilderHelper DefineType(string name, TypeAttributes attrs, Type parent) | |
276 { | |
277 return new TypeBuilderHelper(this, ModuleBuilder.DefineType(name, attrs, parent)); | |
278 } | |
279 | |
280 /// <summary> | |
281 /// Constructs a <see cref="TypeBuilderHelper"/> for a type with the specified name, base type, | |
282 /// and the interfaces that the defined type implements. | |
283 /// </summary> | |
284 /// <param name="name">The full path of the type.</param> | |
285 /// <param name="parent">The Type that the defined type extends.</param> | |
286 /// <param name="interfaces">The list of interfaces that the type implements.</param> | |
287 /// <returns>Returns the created <see cref="TypeBuilderHelper"/>.</returns> | |
288 /// <seealso cref="System.Reflection.Emit.ModuleBuilder.DefineType(string,TypeAttributes,Type,Type[])">ModuleBuilder.DefineType Method</seealso> | |
289 public TypeBuilderHelper DefineType(string name, Type parent, params Type[] interfaces) | |
290 { | |
291 return new TypeBuilderHelper( | |
292 this, | |
293 ModuleBuilder.DefineType(name, TypeAttributes.Public, parent, interfaces)); | |
294 } | |
295 | |
296 /// <summary> | |
297 /// Constructs a <see cref="TypeBuilderHelper"/> for a type with the specified name, its attributes, base type, | |
298 /// and the interfaces that the defined type implements. | |
299 /// </summary> | |
300 /// <param name="name">The full path of the type.</param> | |
301 /// <param name="attrs">The attribute to be associated with the type.</param> | |
302 /// <param name="parent">The Type that the defined type extends.</param> | |
303 /// <param name="interfaces">The list of interfaces that the type implements.</param> | |
304 /// <returns>Returns the created <see cref="TypeBuilderHelper"/>.</returns> | |
305 /// <seealso cref="System.Reflection.Emit.ModuleBuilder.DefineType(string,TypeAttributes,Type,Type[])">ModuleBuilder.DefineType Method</seealso> | |
306 public TypeBuilderHelper DefineType(string name, TypeAttributes attrs, Type parent, params Type[] interfaces) | |
307 { | |
308 return new TypeBuilderHelper( | |
309 this, | |
310 ModuleBuilder.DefineType(name, attrs, parent, interfaces)); | |
311 } | |
312 | |
313 #endregion | |
314 } | |
315 } |