David Kennedy’s Tech Ramblings

Just another WordPress.com weblog

Handy trick for disabling Aero in your applications November 13, 2009

Filed under: Uncategorized — dotnetdave @ 9:24 am

Having only recently moved to the 64bit fold following the purchase of a new PC, I’ve just come across the following useful trick to disable Aero. (Discovered on http://www.codeproject.com/KB/vista/controllingaero.aspx) If you want to ensure compatibility with Vista/Win7 users, or you are having problems as a result of Aero (for example, some DirectX function calls may fail if Aero is active on the desktop running your app) then the following may come in very handy:

    public static class AeroController
    {
        public static readonly uint DWM_EC_DISABLECOMPOSITION = 0;
        public static readonly uint DWM_EC_ENABLECOMPOSITION = 1;
        [DllImport("dwmapi.dll", EntryPoint = "DwmEnableComposition")]
        extern static uint WinDwmEnableComposition(uint uCompositionAction);
        /// <summary>
        /// Enables or Disables Aero on Vista or Win7, required for some compatibility issues
        /// </summary>
        /// <param name="enable">if set to <c>true</c> [enable].</param>
        /// <returns></returns>
        public static bool ControlAero(bool enable)
        {
            try
            {
                if (enable)
                    WinDwmEnableComposition(DWM_EC_ENABLECOMPOSITION);
                if (!enable)
                    WinDwmEnableComposition(DWM_EC_DISABLECOMPOSITION);

                return true;
            }
            catch { return false; }
        }
    }

Once added to your project, you can then simply enable/disable Aero with a call such as:

AeroController.ControlAero(false);
 

My Dual-boot nightmare (and a procedure to shrink partition/LVM2/ext4) November 7, 2009

Filed under: Uncategorized — dotnetdave @ 10:10 pm

Yesterday I decided to install Windows 7 natively, aiming for a dual-boot between Fedora 11 & Win 7. Obviously I was aware that windows installers always wipe the MBR with its own boot loader, destroying any loader which plays well with others (just about any OS besides Windows), so I took backups of the MBR (both with and without the partition table, or so I thought):

dd if=/dev/hda of=/home/David/mbr_backup_nopart bs=446 count=1  (just the MBR without the partition table)
I copied this file to a USB memory stick so I would be able to access it following the Win7 install

I then performed the following procedure (worked perfectly) to shrink file systems, logical volumes, and finally the physical partitions:
  1. Boot to any linux Live CD (I used Ubuntu, if your Live CD doesn’t automatically give you sudoer, authenticate as root and drop the ’sudo’ prefixes)
  2. sudo lvm vgchange -a y (enable logical volume management, since my Fedora install uses LVM2)
  3. sudo fsck -fC /dev/vg_davesdualcore/lv_root (check the file system which I am about to resize)
  4. sudo resize2fs -p /dev/vg_davesdualcore/lv_root  250G (shrink the ext4 file system to use half my hard drive)
  5. sudo lvresize /dev/vg_davesdualcore/lv_root –size 250G (shrink the logical volume accordingly)
  6. sudo lvs (to report the size of your logical volumes, we are after the size of the /swap volume)
  7. sudo lvremove /dev/vg_davesdualcore/lv_swap (remove the swap volume so it can be recreated at the start of the newly available space)
  8. sudo lvcreate –size 3.8G –name lv_swap vg_davesdualcore (recreate the swap partition)
  9. sudo mkswap /dev/vg_davesdualcore/lv_swap (set up a linux swap area on the re-created volume)
  10. sudo pvs (report use and calculate the size the partition can be reduced to, ie. PSize – PFree)
  11. sudo pvresize /dev/sda2 –setphysicalvolumesize 254G (resize the physical volume to free up space at the end of the partition)
  12. sudo pvs –units s  (list physical volumes with size specified in sectors, note PSize)
  13. sudo parted /dev/sda unit s print (print the physical disk partitions with Start, End, & Size in sectors)
  14. Calculate the new End sector (Start from step 13 + PSize from step 12, add at least 32MB/65536 sectors as an error margin)
  15. sudo parted /dev/sda rm 2 (Remove the entry from the partition table. The number is the partition number as listed from step 13)
  16. sudo parted /dev/sda mkpart primary 409663s 533487742s (recreate the partition with the original Start & newly calculate End from step 14)
  17. sudo parted /dev/sda set 2 lvm on (enable logical volume management, again the number is the partition number)
  18. Done! You can view your new structure with ‘parted /dev/sda print’ and/or ‘fdisk -l /dev/sda’
Following this, I inserted a Windows 7 Pro DVD & rebooted. The windows installation completed successfully and I ended up with a working windows 7.

Now, as mentioned at the start of this blog post, the windows installation wiped the MBR. And this is where my nightmare begins..
I attempted to restore the MBR using the following shell command from an Ubuntu Live CD:
(STORE N GO is the volume name of the memory stick I used)

dd if=/media/STORE\'N\'GO/mbr_backup_nopart of=/dev/sda bs=446 count=1
And rebooted..
Much to my dismay I was greeted with the 'Invalid System Disk' message. Fedora 11 still boots following this message however (guess its some sort of BIOS fail-over mechanism), but I am so far unable to get Windows 7 booting from GRUB

When I restored the MBR, it apparently reverted the size of my PV to use most of the disk space again. I re-ran pvresize to set this back, but no luck on the Windows 7 front yet. Looks like I might be up for a complete re-install after all :(

 

Persisting Specifications – Metalinq September 4, 2009

Filed under: Uncategorized — dotnetdave @ 10:00 pm

Something that I utilised several months back for a CEP (complex event processing) project, this is based on the project available at http://metalinq.codeplex.com/

It also requires a more recent version of LinqKit, the one which includes a PredicateBuilder which operates with Expression<Func<T, bool>> rather than Predicate<T> as per older versions of LinqKit.

In short, this allows us to persist and re-hydrate expressions, allowing us to entirely separate our specification from our data. Consider the following example:

 

using System; using System.Collections.Generic; using System.Linq; using System.Text; using LinqKit; using System.Linq.Expressions; using System.Xml.Serialization; using System.IO; using ExpressionBuilder; namespace Org.Suresoft.RulesEngine { public class ScratchClass { public string SomeProp { get; set; } public int SomeNumber { get; set; } } public class ScratchPad { public void DoStuff() { Expression<Func<ScratchClass, bool>> testing = PredicateBuilder.False<ScratchClass>(); EditableExpression expB = EditableExpression.CreateEditableExpression(testing); XmlSerializer serial = new XmlSerializer(typeof(EditableLambdaExpression)); StringBuilder sb = new StringBuilder(); TextWriter writer = new StringWriter(sb); serial.Serialize(writer, expB); var recovered = serial.Deserialize(new StringReader(sb.ToString())) as EditableExpression; var done = recovered.ToExpression() as LambdaExpression; } } }

As you can see, the ability to build up our specifications following the predicate pattern and serialize/deserialize same opens up a whole world of possibilities. In the case of our project, we utilised a Spring-injected repository which in turn made use of Fluent nHibernate for persistence.

 

Microsoft Application Updater Block December 17, 2008

Filed under: Uncategorized — dotnetdave @ 10:37 am

I’m currently utilising the self updating facilities of this technology and had a problem with my configuration. The really confusing part was that it was passing validation just fine, but then falling over actually deserializing the <UpdaterConfiguration> section.

It turned out to be simply a couple of extra lines of white space that was included in the section; eliminating the redundant space got the updater up and running. :)

 

Silverlight, WCF, and Linq to Sql September 18, 2008

Filed under: Silverlight Tutorials — dotnetdave @ 3:52 am

Whilst putting together the Silverlight datagrid sample from a few posts ago, I came across some odd behaviour with my LINQ entity ‘losing’ its schema definition on the client, resulting in the Grid not displaying the data. I’ll explain my approach by way of diagrams:

silverlinq1 silverlinq2

It seems as if the proxy classes for my LINQ entities were not being properly recognised on the client because of the nested WCF calls. I’m still unsure as to the exact cause of this issue, I verified that appropriate attributes added to my LINQ entity classes to support WCF were being propagated to the proxies built from them, however the only way I could get the Grid to successfully display data was by removing the additional tier.

 

POCO2HTML Form Generator September 11, 2008

Filed under: Uncategorized — dotnetdave @ 2:54 am

I sometimes wake up in the early hours of the morning with some idea running around in my head, and this morning it just happened to be this. I have had similar thoughts in the past, as would have most developers who become bored with the repetition of writing input HTML forms that directly match model classes for your data. Here is a working start to a command line utility that reflects on a given assembly and produces simple HTML forms to match.

When I have some more spare time after my 70-536 MS exam I’d like to tidy this up to make it more useable as well as generating c# code to populate an object from the form back on the server. As I’ve been experimenting with the new ASP.NET MVC this is generating a plain HTML form, however the output could easily be adapted to produce rich server controls for input.

Here’s the code so far:

using System; using System.Collections.Generic; using System.Linq; using System.Text; using keithfletcher.org; // courtesy of http://sql.codeproject.com/KB/dialog/CmdLineParsing.aspx using System.IO; using System.Reflection; namespace DotNetDave.Tools.POCO2HTML { [Application( HelpOptions = new string[] { "?", "help" }, OptionPrefixes = new char[] { '/', '-' }, ThrowParsingExceptions = false)] [Option("ns", ShortDescription = "Namespace", LongDescription = "The Namespace which contains Model classes from which to generate HTML forms.", ValuePresence = OptionAttributeValuePresence.MustHaveValue, IsOptional = true)] [Option("class", ShortDescription = "Class", LongDescription = "The fully-qualified class from which to generate a HTML form.", ValuePresence = OptionAttributeValuePresence.MustHaveValue, IsOptional = true)] [Option("all", ShortDescription = "AllTypes", LongDescription = "Generates HTML forms for ALL types in the given Assembly", ValuePresence = OptionAttributeValuePresence.MustNotHaveValue, IsOptional = true)] [Option("SourceFile", IsAnonymous = true, ShortDescription = "FileName", LongDescription = "The Assembly containing the Model/s to generate HTML form/s for.", ValuePresence = OptionAttributeValuePresence.MustHaveValue, IsOptional = false)] public class Program : CommandLineBase { static void Main(string[] args) { new Program(args); } private Program(string[] args) : base(args) { if ((Options.Count == 0) && !ShowingHelp) ShowHelp(); if (ParseErrors && !ShowingHelp) { WriteLine("Errors occurred!"); ShowHelp(); } // verify that the assembly exists if (!ShowingHelp && !File.Exists(Options["SourceFile"].Value)) { WriteLine("Source file specified is invalid! Please check the path and try again"); ShowHelp(); } // continue unless there's a problem if (!ShowingHelp) { Assembly source = Assembly.LoadFrom(Options["SourceFile"].Value); // if a class is specified, use it if (Options["class"].HasValue) { Type t = source.GetType(Options["class"].Value, false, true); ClassHtmlGenerator.Process(t); } else if (Options["ns"].HasValue) WriteLine("Not Yet Implemented"); else { if (Options["all"].IsPresent) { Type[] Types = source.GetTypes(); // generate for all types foreach (Type t in Types) { ClassHtmlGenerator.Process(t); } } else // list all available types { WriteLine("Available Types in Assembly:"); Type[] Types = source.GetTypes(); // Display all the types contained in the specified assembly. foreach (Type t in Types) { Console.WriteLine(t.Name + " (" + t.FullName + ")"); } } } WriteLine("Processing Complete!"); } Console.ReadKey(); } } public class ClassHtmlGenerator { public static void Process(Type SourceClass) { PropertyInfo[] props = SourceClass.GetProperties(); if (props.Count() == 0) return; // ignore types with no properties // start a target file StreamWriter target = new StreamWriter(SourceClass.Name + "Form.html"); target.WriteLine("<form id=\"Form1\">"); target.WriteLine("<table width=\"90%\">"); foreach (PropertyInfo prop in props) { if (prop.CanWrite) { target.Write("<tr><td>" + prop.Name + "</td>"); if (prop.PropertyType == typeof(string)) target.WriteLine("<td><input type=\"text\" name=\"" + prop.Name + "\"></td></tr>"); else if (prop.PropertyType == typeof(bool)) target.WriteLine("<td><input type=\"checkbox\" name=\"" + prop.Name + "\"></td></tr>"); else if (prop.PropertyType == typeof(DateTime)) // include simple datetime picker target.WriteLine("<td><input type=\"text\" name=\"" + prop.Name + "\"></td></tr>"); else if (prop.PropertyType.IsEnum) // offer options { target.Write("<td><select name=\"" + prop.Name + "\">"); foreach (FieldInfo fInfo in prop.PropertyType.GetFields(BindingFlags.Public | BindingFlags.Static)) { target.Write("<option value=\"{0}\">{1}</option>", fInfo.GetRawConstantValue().ToString(), fInfo.Name); } target.WriteLine("</select></td></tr>"); } else if (prop.PropertyType.IsValueType) // default to text input for now target.WriteLine("<td><input type=\"text\" name=\"" + prop.Name + "\"></td></tr>"); } } target.WriteLine("</table></form>"); target.Flush(); target.Close(); } } }

 

You’ll need to include the CmdLineParsing project from:

 http://sql.codeproject.com/KB/dialog/CmdLineParsing.aspx

An example of the input and output is as follows:

public class TestClass { public enum StatusEnum { good, bad, ugly }; public string Title { get; set; } public StatusEnum Status { get; set; } public bool Active { get; set; } }

And this will produce the following form:

<form id="Form1"> <table width="90%"> <tr><td>Title</td><td><input type="text" name="Title"></td></tr> <tr><td>Status</td><td><select name="Status"><option value="0">good</option><option value="1">bad</option><option value="2">ugly</option> </select></td></tr> <tr><td>Active</td><td><input type="checkbox" name="Active"></td></tr> </table></form>
 

Good little Silverlight Tutorials September 2, 2008

Filed under: Silverlight Tutorials — dotnetdave @ 9:02 am

This has some good stuff on it, quick little introductions into various areas of the visual side of Silverlight

http://www.nibblestutorials.net/

 

Silverlight Adventures Part 2 August 26, 2008

Filed under: Silverlight Tutorials — dotnetdave @ 12:29 am

The Grid

Ok, for this exercise we start with a new Silverlight project (you can create this in either Expression Blend or Visual Studio). Next, we want to add a reference to system.windows.controls.data (to make the datagrid control accessible) before dragging the new Silverlight Datagrid control onto the page, producing xaml as follows:

<UserControl xmlns:my="clr-namespace:System.Windows.Controls;assembly=System.Windows.Controls.Data" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" x:Class="SilverGridClient.Page" Width="640" Height="480"> <Grid x:Name="LayoutRoot" Background="White"> <my:DataGrid x:Name="dg" AutoGenerateColumns="True"></my:DataGrid> </Grid> </UserControl>

Next, we want to add a WCF Service project to the solution within VS. As a data source for our grid I’ve opted for a simple LinQ to SQL dbml, so add a new ‘LINQ to SQL Classes’ item to the WCF project. From server explorer, define a connection to any DB that has some data in it, and drag a populated table onto the designer. Since we are passing this type via our WCF service, we need to decorate the generated LinQ classes (in the designer.cs file) with the DataContract attribute. Open the Web.config for the WCF service & ensure that the service endpoint is defined with basicHttpBinding as the binding attribute. Finally, we need to define a method to return data for our grid. In my case I was using a table specifiying documents from a recent project I was involved with, so I added a method as follows:

public List<FreestyleDocument> GetAllDocuments() { SilverLinqDataContext linq = new SilverLinqDataContext("Server=.;Database=Data_DavesJuly;Integrated Security=true"); return linq.FreestyleDocuments.Take(500).ToList(); }

Now build the WCF service.

Next we need to generate a proxy for our service, so we want to add a service reference to our WCF service from the Silverlight project. Kick up the WCF service (or host it in IIS if you prefer) and navigate to the service endpoint from the ‘Add Service Reference’ context option. This will create our proxy as well as a ServiceReferences.ClientConfig file defining the endpoint. Finally, we want to include the call via the proxy to our WCF service method which we have defined in order to populate the grid view. Do this in the Page.xaml.cs file; in my case the code looked like this:

public Page() { //InitializeComponent(); SilverProxy.Service1Client webService = new SilverProxy.Service1Client(); webService.GetAllDocumentsCompleted += new EventHandler<SilverProxy.GetAllDocumentsCompletedEventArgs>(webService_GetUsersCompleted); webService.GetAllDocumentsAsync(); } void webService_GetUsersCompleted(object sender, SilverProxy.GetAllDocumentsCompletedEventArgs e) { dg.ItemsSource = e.Result; }

At this stage it would be possible for the Silverlight application to directly access our WCF service if it weren’t for the browser-side sand-boxing which prevent cross domain calls. Attempting to run the application now will result in something similar to the following error:

An error occurred while trying to make a request to URI ‘http://localhost/SilverService/Service1.svc’. This could be due to a cross domain configuration error. Please see the inner exception for more details.

According to online documentation, this problem should be averted by including one or both of the following configuration override files in the root of the hosting web server (in my case I hosted the service in IIS to make this process simpler):

crossdomain.xml:

<?xml version="1.0"?> <!DOCTYPE cross-domain-policy SYSTEM "http://www.macromedia.com/xml/dtds/cross-domain-policy.dtd"> <cross-domain-policy> <allow-http-request-headers-from domain="*" headers="*"/> </cross-domain-policy>

clientaccesspolicy.xml

<?xml version="1.0" encoding="utf-8" ?> <access-policy> <cross-domain-access> <policy> <allow-from http-request-headers="*"> <domain uri="*"/> </allow-from> <grant-to> <resource path="/" include-subpaths="true"/> </grant-to> </policy> </cross-domain-access> </access-policy>

In my case neither of these files made any difference; I continued to receive the cross domain call error. Failing this approach, the next step is to institute an intermediate proxy on the server side of our Silverlight project, thus negating the cross domain call from the browser. After moving the Linq2Sql ORM & WCF service into the main ASP.NET site which included the Silverlight application the datagrid was bound to the data as expected.

 

Getting Reporting Services running under Vista August 13, 2008

Filed under: Tech Tips — dotnetdave @ 1:33 am

My environment is Vista Ultimate 32 bit, with IIS & ASP.NET already configured for VS development.

You need to install Sql Server 2005 SP2 AFTER including the Reporting Services component in the original Sql Server installer (this can be added separately, but you still need to run SP2 again as it updates the Reporting Services)

Next you must remove an extra slash from the ‘AboMapperCustom’ Handler entry under the ReportServer site from within IIS Manager.

ie. C:\Windows\Microsoft.NET\Framework\v2.0.50727\\aspnet_isapi.dll -> C:\Windows\Microsoft.NET\Framework\v2.0.50727\aspnet_isapi.dll

Run the Reporting Services Configuration Manager and ensure that the virtual directories & database is setup correctly, do so as required

Verify permissions to the rsreportserver.config file in the ReportingServices\ReportServer directory under your Sql Server installation (I took the sledgehammer approach and added ‘Everyone’ for Read/Execute permissions)

That was enough to get me up and running! :)

 

Silverlight Pacman! August 13, 2008

Filed under: Silverlight Tutorials — dotnetdave @ 12:29 am

I’ve finally got my pacman game hosted on live.com :)

http://silverlight.services.live.com/invoke/75950/Pacman/iframe.html