PageRenderTime 46ms CodeModel.GetById 21ms RepoModel.GetById 0ms app.codeStats 0ms

/client_v4_2_dev/Framework/CorDebug/ResXFileCodeGenerator.cs

#
C# | 396 lines | 322 code | 67 blank | 7 comment | 58 complexity | 74545c1da0e1564f9005828fb566473f MD5 | raw file
Possible License(s): Apache-2.0, LGPL-2.0, MIT, MPL-2.0-no-copyleft-exception
  1. using System;
  2. using System.IO;
  3. using System.Reflection;
  4. using System.Diagnostics;
  5. using System.Collections;
  6. using System.ComponentModel;
  7. using System.Runtime.InteropServices;
  8. using CorDebugInterop;
  9. using Microsoft.Win32;
  10. using Microsoft.VisualStudio.Debugger.Interop;
  11. using Microsoft.VisualStudio.Shell.Interop;
  12. using Microsoft.VisualStudio.Shell;
  13. using Microsoft.VisualStudio.OLE.Interop;
  14. using Microsoft.VisualStudio.Designer.Interfaces;
  15. using System.CodeDom;
  16. using System.CodeDom.Compiler;
  17. using IOleServiceProvider = Microsoft.VisualStudio.OLE.Interop.IServiceProvider;
  18. using IServiceProvider = System.IServiceProvider;
  19. namespace Microsoft.SPOT.Debugger
  20. {
  21. internal abstract class BaseCodeGenerator : IVsSingleFileGenerator
  22. {
  23. private string codeFileNameSpace = string.Empty;
  24. private string codeFilePath = string.Empty;
  25. private IVsGeneratorProgress codeGeneratorProgress;
  26. // **************************** PROPERTIES ****************************
  27. protected string FileNameSpace
  28. {
  29. get
  30. {
  31. return codeFileNameSpace;
  32. }
  33. }
  34. protected string InputFilePath
  35. {
  36. get
  37. {
  38. return codeFilePath;
  39. }
  40. }
  41. internal IVsGeneratorProgress CodeGeneratorProgress
  42. {
  43. get
  44. {
  45. return codeGeneratorProgress;
  46. }
  47. }
  48. // **************************** METHODS **************************
  49. public abstract int DefaultExtension( out string ext );
  50. // MUST implement this abstract method.
  51. protected abstract byte[] GenerateCode( string inputFileName, string inputFileContent );
  52. protected virtual void GeneratorErrorCallback( int warning, uint level, string message, uint line, uint column )
  53. {
  54. IVsGeneratorProgress progress = CodeGeneratorProgress;
  55. if(progress != null)
  56. {
  57. Utility.COM_HResults.ThrowOnFailure( progress.GeneratorError( warning, level, message, line, column ) );
  58. }
  59. }
  60. public int Generate( string wszInputFilePath, string bstrInputFileContents, string wszDefaultNamespace,
  61. IntPtr[] pbstrOutputFileContents, out uint pbstrOutputFileContentSize, IVsGeneratorProgress pGenerateProgress )
  62. {
  63. if(bstrInputFileContents == null)
  64. {
  65. throw new ArgumentNullException( bstrInputFileContents );
  66. }
  67. codeFilePath = wszInputFilePath;
  68. codeFileNameSpace = wszDefaultNamespace;
  69. codeGeneratorProgress = pGenerateProgress;
  70. byte[] bytes = GenerateCode( wszInputFilePath, bstrInputFileContents );
  71. if(bytes == null)
  72. {
  73. pbstrOutputFileContents[0] = IntPtr.Zero;
  74. pbstrOutputFileContentSize = 0;
  75. }
  76. else
  77. {
  78. pbstrOutputFileContents[0] = Marshal.AllocCoTaskMem( bytes.Length );
  79. Marshal.Copy( bytes, 0, pbstrOutputFileContents[0], bytes.Length );
  80. pbstrOutputFileContentSize = (uint)bytes.Length;
  81. }
  82. return Utility.COM_HResults.S_OK;
  83. }
  84. protected byte[] StreamToBytes( Stream stream )
  85. {
  86. if(stream.Length == 0)
  87. return new byte[] { };
  88. long position = stream.Position;
  89. stream.Position = 0;
  90. byte[] bytes = new byte[(int)stream.Length];
  91. stream.Read( bytes, 0, bytes.Length );
  92. stream.Position = position;
  93. return bytes;
  94. }
  95. }
  96. internal abstract class BaseCodeGeneratorWithSite : BaseCodeGenerator, IObjectWithSite
  97. {
  98. private Object site = null;
  99. private CodeDomProvider codeDomProvider = null;
  100. private static Guid CodeDomInterfaceGuid = new Guid( "{73E59688-C7C4-4a85-AF64-A538754784C5}" );
  101. private static Guid CodeDomServiceGuid = CodeDomInterfaceGuid;
  102. private ServiceProvider serviceProvider = null;
  103. protected virtual CodeDomProvider CodeProvider
  104. {
  105. get
  106. {
  107. if(codeDomProvider == null)
  108. {
  109. IVSMDCodeDomProvider vsmdCodeDomProvider = (IVSMDCodeDomProvider)GetService( CodeDomServiceGuid );
  110. if(vsmdCodeDomProvider != null)
  111. {
  112. codeDomProvider = (CodeDomProvider)vsmdCodeDomProvider.CodeDomProvider;
  113. }
  114. Debug.Assert( codeDomProvider != null, "Get CodeDomProvider Interface failed. GetService(QueryService(CodeDomProvider) returned Null." );
  115. }
  116. return codeDomProvider;
  117. }
  118. set
  119. {
  120. if(value == null)
  121. {
  122. throw new ArgumentNullException();
  123. }
  124. codeDomProvider = value;
  125. }
  126. }
  127. private ServiceProvider SiteServiceProvider
  128. {
  129. get
  130. {
  131. if(serviceProvider == null)
  132. {
  133. IOleServiceProvider oleServiceProvider = site as IOleServiceProvider;
  134. Debug.Assert( oleServiceProvider != null, "Unable to get IOleServiceProvider from site object." );
  135. serviceProvider = new ServiceProvider( oleServiceProvider );
  136. }
  137. return serviceProvider;
  138. }
  139. }
  140. protected Object GetService( Guid serviceGuid )
  141. {
  142. return SiteServiceProvider.GetService( serviceGuid );
  143. }
  144. protected object GetService( Type serviceType )
  145. {
  146. return SiteServiceProvider.GetService( serviceType );
  147. }
  148. public override int DefaultExtension( out string ext )
  149. {
  150. CodeDomProvider codeDom = CodeProvider;
  151. Debug.Assert( codeDom != null, "CodeDomProvider is NULL." );
  152. string extension = codeDom.FileExtension;
  153. if(extension != null && extension.Length > 0)
  154. {
  155. if(extension[0] != '.')
  156. {
  157. extension = "." + extension;
  158. }
  159. }
  160. ext = extension;
  161. return Utility.COM_HResults.S_OK;
  162. }
  163. protected virtual ICodeGenerator GetCodeWriter()
  164. {
  165. CodeDomProvider codeDom = CodeProvider;
  166. if(codeDom != null)
  167. {
  168. #pragma warning disable 618 //backwards compat
  169. return codeDom.CreateGenerator();
  170. #pragma warning restore 618
  171. }
  172. return null;
  173. }
  174. // ******************* Implement IObjectWithSite *****************
  175. //
  176. public virtual void SetSite( object pUnkSite )
  177. {
  178. site = pUnkSite;
  179. codeDomProvider = null;
  180. serviceProvider = null;
  181. }
  182. // Does anyone rely on this method?
  183. public virtual void GetSite( ref Guid riid, out IntPtr ppvSite )
  184. {
  185. if(site == null)
  186. {
  187. Utility.COM_HResults.Throw( Utility.COM_HResults.E_FAIL );
  188. }
  189. IntPtr pUnknownPointer = Marshal.GetIUnknownForObject( site );
  190. try
  191. {
  192. Marshal.QueryInterface( pUnknownPointer, ref riid, out ppvSite );
  193. if(ppvSite == IntPtr.Zero)
  194. {
  195. Utility.COM_HResults.Throw( Utility.COM_HResults.E_NOINTERFACE );
  196. }
  197. }
  198. finally
  199. {
  200. if(pUnknownPointer != IntPtr.Zero)
  201. {
  202. Marshal.Release( pUnknownPointer );
  203. pUnknownPointer = IntPtr.Zero;
  204. }
  205. }
  206. }
  207. }
  208. internal class ResXFileCodeGenerator : BaseCodeGeneratorWithSite, IObjectWithSite
  209. {
  210. internal const string c_Name = "ResXFileCodeGenerator";
  211. private const string DesignerExtension = ".Designer";
  212. internal bool m_fInternal = true;
  213. internal bool m_fNestedEnums = true;
  214. internal bool m_fMscorlib = false;
  215. VsProject _project;
  216. public ResXFileCodeGenerator(VsProject vsProject)
  217. {
  218. _project = vsProject;
  219. }
  220. protected string GetResourcesNamespace()
  221. {
  222. string resourcesNamespace = null;
  223. try
  224. {
  225. IntPtr punkVsBrowseObject;
  226. Guid vsBrowseObjectGuid = typeof( IVsBrowseObject ).GUID;
  227. GetSite( ref vsBrowseObjectGuid, out punkVsBrowseObject );
  228. if(punkVsBrowseObject != IntPtr.Zero)
  229. {
  230. IVsBrowseObject vsBrowseObject = Marshal.GetObjectForIUnknown( punkVsBrowseObject ) as IVsBrowseObject;
  231. Debug.Assert( vsBrowseObject != null, "Generator invoked by Site that is not IVsBrowseObject?" );
  232. Marshal.Release( punkVsBrowseObject );
  233. if(vsBrowseObject != null)
  234. {
  235. IVsHierarchy vsHierarchy;
  236. uint vsitemid;
  237. vsBrowseObject.GetProjectItem( out vsHierarchy, out vsitemid );
  238. Debug.Assert( vsHierarchy != null, "GetProjectItem should have thrown or returned a valid IVsHierarchy" );
  239. Debug.Assert( vsitemid != 0, "GetProjectItem should have thrown or returned a valid VSITEMID" );
  240. if(vsHierarchy != null)
  241. {
  242. object obj;
  243. vsHierarchy.GetProperty( vsitemid, (int)__VSHPROPID.VSHPROPID_DefaultNamespace, out obj );
  244. string objStr = obj as string;
  245. if(objStr != null)
  246. {
  247. resourcesNamespace = objStr;
  248. }
  249. }
  250. }
  251. }
  252. }
  253. catch(Exception e)
  254. {
  255. Debug.WriteLine( e.ToString() );
  256. Debug.Fail( "These methods should succeed..." );
  257. }
  258. return resourcesNamespace;
  259. }
  260. public override int DefaultExtension( out string ext )
  261. {
  262. //copied from ResXFileCodeGenerator
  263. string baseExtension;
  264. ext = String.Empty;
  265. int hResult = base.DefaultExtension( out baseExtension );
  266. if(!Utility.COM_HResults.SUCCEEDED( hResult ))
  267. {
  268. Debug.Fail( "Invalid hresult returned by the base DefaultExtension" );
  269. return hResult;
  270. }
  271. if(!String.IsNullOrEmpty( baseExtension ))
  272. {
  273. ext = DesignerExtension + baseExtension;
  274. }
  275. return Utility.COM_HResults.S_OK;
  276. }
  277. protected override byte[] GenerateCode( string inputFileName, string inputFileContent )
  278. {
  279. VSLangProj.Reference reference = _project.VSLangProj_References.Find("System.Drawing");
  280. if (reference != null)
  281. {
  282. reference.Remove();
  283. }
  284. string spotGraphics = "Microsoft.SPOT.Graphics";
  285. reference = _project.VSLangProj_References.Find(spotGraphics);
  286. if (reference == null)
  287. {
  288. _project.VSLangProj_References.Add(spotGraphics);
  289. }
  290. MemoryStream stream = new MemoryStream();
  291. StreamWriter writer = new StreamWriter( stream );
  292. string inputFileNameWithoutExtension = Path.GetFileNameWithoutExtension( inputFileName );
  293. Assembly tasks = null;
  294. foreach (Assembly asm in AppDomain.CurrentDomain.GetAssemblies())
  295. {
  296. if (string.Compare(asm.GetName().Name, "Microsoft.SPOT.Tasks", true) == 0)
  297. {
  298. if(asm.GetName().Version.ToString(2) == new Version(_project.GetTargetFrameworkProperty().TrimStart('v')).ToString(2))
  299. {
  300. tasks = asm;
  301. break;
  302. }
  303. }
  304. }
  305. if (tasks == null) throw new Exception("Microsoft.SPOT.Tasks.dll is not loaded!");
  306. Type typ = tasks.GetType("Microsoft.SPOT.Tasks.ProcessResourceFiles");
  307. if (typ != null)
  308. {
  309. object processResourceFiles = typ.GetConstructor(new Type[]{}).Invoke(null);
  310. typ.GetProperty("StronglyTypedClassName").SetValue(processResourceFiles, inputFileNameWithoutExtension, null);
  311. typ.GetProperty("StronglyTypedNamespace").SetValue(processResourceFiles, GetResourcesNamespace(), null);
  312. typ.GetProperty("GenerateNestedEnums").SetValue(processResourceFiles, m_fNestedEnums, null);
  313. typ.GetProperty("GenerateInternalClass").SetValue(processResourceFiles, m_fInternal, null);
  314. typ.GetProperty("IsMscorlib").SetValue(processResourceFiles, m_fMscorlib, null);
  315. string resourceName = (string)typ.GetProperty("StronglyTypedNamespace").GetValue(processResourceFiles, null);
  316. if (string.IsNullOrEmpty(resourceName))
  317. {
  318. resourceName = inputFileNameWithoutExtension;
  319. }
  320. else
  321. {
  322. resourceName = string.Format("{0}.{1}", resourceName, inputFileNameWithoutExtension);
  323. }
  324. typ.GetMethod("CreateStronglyTypedResources").Invoke(processResourceFiles, new object[]{ inputFileName, this.CodeProvider, writer, resourceName });
  325. }
  326. return base.StreamToBytes( stream );
  327. }
  328. }
  329. }