Sunday, July 04, 2004

On this day, the United States of America's Independence Day, I am overcome with gratitude for those that sacrificed so much for the country in which I live.  What a wonderful, blessed country!  It is because of their willingness to place their beliefs and even their very lives on the line that I live in such a beautiful place.  I commit to do what I can to live up to their legacy.

Sunday, July 04, 2004 2:25:00 PM (Mountain Standard Time, UTC-07:00)  #    Disclaimer  |  Comments [0]  |  Trackback
 Friday, July 02, 2004

In a recent post Eric Gunnerson points out some important concepts involving .NET assemblies and how they should be packaged to yield the best performance.  Basically, the fewer the better.  Each assembly that your application must load increases it's load time.  That said, one should not simply package all of his classes into a single, massive dll.  That would have a very negative and far-reaching impact.  Way back when I got into .NET development (back when it was it Beta 2) I wanted to understand what assemblies were all about.  A very important conclusion that I came to, and EricGu doesn't fail to bring it up, is that of versioning and security.  All code in the assembly versions at the same rate.  More importantly, however, are the security implications.  All code within an assembly has the same identity (and therefore the same level of trust).  If your assembly has to perform various types of actions (such as file IO, registry access, P/Invoke, all code will ultimately have the ability to perform all of those tasks - which may not be what you're wanting).

Aside from the performance and security implications, there may be very good reasons to partition your assemblies into smaller units of code.  Some components might need to be registered into the GAC, while others might need to reside remotely.  The concept of application layers and tiers comes to mind.  While application tiering is a logical design construct, it can have physical implications.  To enforce business requirements, you might not want the UI (user interface) tier to call directly into the DA (data access) tier (there are exceptions to this cut and dry rule).  Were all your classes in a single dll, there would really not be anything stopping them from doing so.  Of course, even then all the developer has to do is set a reference to your DAL (and with the proper know-how and permissions) go to town.

Developing an assembly as a single gargantuan project may not be the right thing to do.  Sometimes your developers are not geographically together or it simply makes more sense to create and test smaller projects.  Well, if you use the Visual Studio .NET environment for compilation, a project = an assembly.  There's not really a way around that.  Barry Gervin beat me to the punch on writing about this, but it's pretty easy to compile from the command prompt.  What you must do is compile your project files to a NetModule.  Then using the AL (Assembly Linker) utility, link the NetModules together into a single assembly.  (Note, this also makes it quite possible to combine, say VB.NET and C# in the same assembly).

Friday, July 02, 2004 3:33:00 AM (Mountain Standard Time, UTC-07:00)  #    Disclaimer  |  Comments [0]  |  Trackback
 Monday, June 28, 2004

As a courtesy to developers out there, I'd like to remind all who write and develop Windows applications to take the time to position your windows (forms) properly on the screen.  Not all users have their taskbar on the bottom on the screen.  I am constantly annoyed by applications that assume that 0,0 is the upper left corner of the screen and that it's a safe place to position your windows - especially because I like my task bar along the left side and toolbars across the top.  This configuration is, to me, extremely productive especially with a widescreen monitor.

The list of applications that don't position themselves correctly is too long to mention, but some tools that I quite frequently use (almost daily) are ILDASM and Virtual PC.  ILDASM has the annoying nuance in that it always starts in the upperleft corner of the screen (0,0) so the entire titlebar always appears (or rather doesn't appear) completely obscured beneath the taskbar/toolbars - thank goodness for the ALT key and system menus.  Virtual PC never quite stays in the same place, creeping towards 0,0 each time you open it.

It's not hard to get it right.  If your application requires manual placement of the form you simply need to call Screen.GetWorkingArea([form variable]) to get the screen on which (the majority of) your form is positioned.  Then you can do a little magic otherwise known as basic math and you have it.

The following example identifies how to do this:

using System;
using System.Drawing;
using System.Windows.Forms;

namespace WorkingAreaTest {
   public sealed class EntryPoint {

      [STAThread()]
      public static void Main() {
         Form f = new Form();
         f.StartPosition = FormStartPosition.Manual;
         Rectangle rct = Screen.PrimaryScreen.WorkingArea;
         // you could also call Screen.GetWorkingArea(f)
   
         // to center the form on the screen
         // by bitshifting to divide by 2, we get two benefits:
         // 1) improved performance (negligible here)
         // 2) we don't need to cast the result to an int

         f.Location = new Point(
            (rct.Left + (rct.Width >> 1) - (f.Width >> 1)),
            (rct.Top + (rct.Height >> 1) - (f.Height >> 1)));

         // to position the form on the upperleft corner of the screen
         f.Location = new Point(rct.Left, rct.Top);

         // show the form and get the application running
         Application.Run(f);
      }
   }
}

If you're programming a traditional Windows applications (non-.NET), you can use the SystemParametersInfo() function passing in SPI_GETWORKAREA.

RECT rct;
BOOL ret = SystemParametersInfo(SPI_GETWORKAREA, 0, &rct, 0);

Well, there you go, not much too it at all...and your users will thank you for it, or maybe they'll use your program and never notice you did thim this courtesy - and that's the best praise one could receive.  Believe me, they'll notice if you don't.

Monday, June 28, 2004 3:50:00 AM (Mountain Standard Time, UTC-07:00)  #    Disclaimer  |  Comments [2]  |  Trackback
 Sunday, June 27, 2004

This is pretty common and straightforward (and quite elementary), but can be a gotcha if you're new to software development so I figured it'd be worth blogging about.

When you're assembling your applications you'll be invariably presented with the quandary of whether you should use a struct or a class to represent your data.  This choice isn't often cut and dry.  While in many respects they are semantically similar, there are some distinctions that should be known.

First and foremost, perhaps, is how they are allocated in memory.  Structs, by nature, are ValueType objects and are loaded onto the application's stack.  Class instances, on the other hand reference types and are heap-allocated.  A nicety of stack-allocated objects is that they are automatically taken care of when a procedure finishes (unless you move the object to the heap).  They are more deterministic in that respect.  Memory, however, is finite, and the stack is much smaller than the heap so you're limited to how many objects you can load onto it.  Stack allocations are faster than heap allocations as well, though the .NET runtime has some advanced memory assignment and allocation algorithms that make heap allocations nearly (almost imperceptively) as fast as stack allocations.  Okay, enough about that.

There are some other marked differences between the two:

Constructors:  In a struct you can define constructors, but the constructors be parameterized; you cannot create a parameterless constructor as you can with a class.

Fields:  Within a struct you can define fields, but initialization of the field's value in the declaration is not acceptable.  An exception to this is that static fields can be initialized.

As a parameter:  Another important distinction between the two is their behavior when passed as a parameter to a method.  When you pass a struct, it is passed by value (that is, it's copied) whereas a class instance is passed by reference (the reference is copied - not the object).  This has some far-reaching implications.  Suppose you have the following scenario, ignoring the fact that a similar struct may already exist in the .NET framework (it's just for illustration purposes):

struct Coords {
   public int x;
   public int y;

   public Coords(int xCoord, int yCoord) {
      x = xCoord;
      y = yCoord;
   }
}

public static void Main() {
   Coords pt = new Coords(10, 10);
   movePt(pt, 5, 3);
   // what is the value of pt.x and pt.y here?
}

private static movePt(Coords pt, int xOffset, int yOffset) {
   pt.x += xOffset;
   pt.y += yOffset;
}

When you call movePt() pt is copied so the method is affecting a different pt than the one passed in (though the values are the same).  Now, this may be exactly the functionality you want, but then again it might not.  Sure you can solve your problem by making the parameter a ref parameter, but that's another story, and it might impose some discipline upon the caller.

Interfaces:  Ok, now this is potentially a bit more confusing for the novice, but here goes.  Structs, just like classes, can implement interfaces.  This adds a twist to the ValueType / reference type relationship.  When you cast a struct to its interface, the struct is boxed; it is copied up to the managed heap.  Changes made to it through the interface affect the boxed copy.  The struct is never unboxed back to the struct (unless you explicitly unbox it).  Let's see this in action (Okay, okay, I know the names are stupid, but hey, it's all off the cuff):

interface IIncrementer {
   void AddValue(int value);
}

struct IntWrapper : IIncrementer {
   private int _value;

   public IntWrapper(int value) {
      _value = value;
   }

   void IIncrementer.AddValue(int value) {
      _value += value;
   }

   public int Value {
      get { return _value; }
   }
}

public sealed class EntryPoint {
   public static void Main() {
      IntWrapper iw = new IntWrapper(5);   // the initial value is 5
      ((IIncrementer)iw).AddValue(3);      // the value of iw is still 5!  the
                                           // change to the value happened on the
                                           // heap copy and was immediately
                                           // discarded!

      // box and unbox example:
      IIncrementer iiw = (IIncrementer)iw; // box it and obtain a reference
      iiw.AddValue(4);                     // increment the boxed copy
      iw = (IntWrapper)iiw;                // unbox it, replacing the stack copy.
                                           // the value is now 9!
   }
}

Personally, I find the class model (vs the struct model) much more intuitive and welcoming, but structs definitely have their place - I use them all the time.  When it comes down to it, though, I think that one of the interesting characteristics of structs is that they have meaning or state in their default, unitialized form.  That is, the default state of a struct must have some intuitiveness upon creation (you can't control it's default constructor, nor can you deny someone from creating an instance without parameters).  You don't want someone creating an instance of your struct and calling a method or referencing a field/property and having it throw.  This is where classes and their constructors come in really handy.

Pretty much everything mentioned above focuses on structs that have ValueType members.  The playing field changes a little if you a struct that has reference types (such as Strings or other objects) internally as those are heap allocated objects maintained within a ValueType - now your struct isn't quite as deterministic.

Enjoy!

Sunday, June 27, 2004 6:33:00 AM (Mountain Standard Time, UTC-07:00)  #    Disclaimer  |  Comments [7]  |  Trackback
 Thursday, June 24, 2004

Well, a lot of things have been going on in my life lately, but not much to blog about.  I've been swamped at work and at home, but I hope to be back at the blogging machine from now on.

Over the last several weeks, I have decided to make some changes in my life and career that will have longlasting and (hopefully) beneficial effect on my family.  Yesterday was my last day with my previous employer and I've moved on to be an independent consultant.  This change means that I will be able to spend more time with my family (which is always a bonus) as well as work from home.  I will also be able to spend more time devoted to things that I have been slacking on over the years.

Leaving a steady job and income to the wild unknown is not something that I take lightly.  It was in many respects a very difficult decision to make and I left behind a lot of what I worked for over the years - though it could be said that all that I worked for over the years has led me to this.

Here's to new beginnings and a prosperous future!

Thursday, June 24, 2004 4:38:00 AM (Mountain Standard Time, UTC-07:00)  #    Disclaimer  |  Comments [0]  |  Trackback
 Friday, June 18, 2004

As developers we're constantly faced with the need to crank out good quality code.  This isn't often the easiest task, especially with the mounting need to stay at the forefront of technology.  Visual Studio, while a powerhouse development environment, can only offer so much.  Here is a great list of tools that should be a part of every developer's toolkit.  These tools will aid in the generation of good, quality code and keep the productivity high.  Additionally, Scott Hanselman has his Ultimate Developer and Power Users Tools List, a recommended set of tools that all developers must know how to use.

Of these tools, I have loads of firsthand experience with NDoc (love it!) and FxCop (currently version 1.3) and the Regulator.  I've played with several others.

Some other tools that I really find useful and enjoy are:

Aaron Skonnard's XML Tools

The VS.NET Command Prompt (invaluable - I moved this shortcut to my Start Menu for quick access)

ISO Recorder - invaluable tool for creating images of your CDs

Notepad 2 - A very capable replacement for the boring, ordinary Notepad...try it out! it's awesome!

UltraMagnifier - Excellent tool for giving presentations

What tools do you use?

Friday, June 18, 2004 4:06:00 AM (Mountain Standard Time, UTC-07:00)  #    Disclaimer  |  Comments [0]  |  Trackback
 Thursday, June 17, 2004

Designing applications can be a daunting task.  Even the simplest of utilities can present obstacles and issues unforeseen.  Enterprise-level, distributed applications present problems on a greater scale: security (authentication and authorization), distributed transactional support, object pooling, JIT, just to name a few.  Trying to roll your own infrastructure to support these features reliably is extrememly difficult - go ahead and try.  I think every developer has tried to implement some of these features at least to some degree.  But trying to harness all of these capabilities, especially when they already exist, is asinine and a fool's quest.

Over the past several months, I have been asked repetitively by various individuals (both coworkers as well as friends and associates) whether COM+ is a thing of the past.  I've been told that Microsoft is no longer investing in COM+ services and that it's been deprecated; that Enterprise Services (aka COM+ in the .NET world) is just a COM-interop layer over the actual COM+ implementation provided by the OS.  These statements couldn't be further from the truth.  Enterprise Services is alive and kicking.

As Brian Noyes points out in his blog post, there are a lot of misconceptions about the positioning of Enterprise Services with respect to developing solutions with .NET.  It is frequently viewed as a thing of the past and therefore legacy software that doesn't really have a place in modern software development.  When Microsoft developed COM+ (which, in its inception was Microsoft Transation Server (MTS) and part of the Windows NT 4.0 Option Pack) they were very forward-looking and to their credit succeeded admirably.  If you take the time to read Microsoft's Prescriptive Architecture Guidance (PAG), you'll see that even today in the building of distributed, n-tier applications we are encouraged to use Enterprise Services.

One of the reasons I've heard that discourages its use is the whole COM-interop thing.  There are really two ways in which a COM+ application can run: as a Library application or a Server application.

When a component is a Library application, it runs in-process with the caller.  If you've developed your COM+ component in .NET there is no interop at all.  All calls to your COM+ component are direct, managed C++ calls to the subsystem - this will be very fast, just involving a context switch.

When a component is a Server application, then yes, COM-interop enters the picture.  A Runtime Callable Wrapper (RCW) is created.  It is through this proxy that calls to the object occur.  All in all, this overhead is minimal especially when compared to what the actual function will probably be doing.

With respect to the future, however, is COM+ going away?  Is Microsoft abandoning their flagship component server?  I think not.  When you look at what is up and coming such as Indigo it might appear that COM+ is going by the wayside, in preference to this newer technology.  In fact, COM+ is being enhanced to support calls to an from Indigo for a seamless interoperation in the Longhorn timeframe.

Basically, when it comes down to it, we are still being encouraged to use Enterprise Services in the back-end as the service provider for our applications, inside the service boundaries.  Usually, the recommendation is that the service boundary be actually implemented via another mechanism such as Web Services (eg: ASMX, WSE).

Enterprise Services offer many other benefits that I haven't mentioned here, but I believe that many developers are afraid to embrace the technology for fear of the complexity and breadth of its coverage.  Sure, COM+ can be a bit daunting.  It isn't simple, but as developers it is our responsibility to learn about the various technologies and apply them where they best fit.  I'm convinced that by using COM+ properly our applications will be better prepared for the today as well as for the future.

A few months ago I had the privilege of presenting a talk to our local .NET User Group regarding component development in COM+.  Check out the presentation.

---
Update 06/17/2004:

Some helpful COM+/Enterprise Services links:

GotDotNet COM+ FAQ
DCOM deserves our respect
.NET Enterprise Services Performance
Enterprise Architecturing II

Thursday, June 17, 2004 7:05:00 AM (Mountain Standard Time, UTC-07:00)  #    Disclaimer  |  Comments [0]  |  Trackback
 Wednesday, June 16, 2004

As a seasoned component developer I was a bit disappointed when I first made the move to .NET with respect to (really only) one thing:  the ability to scope the property getters and setters individually.  Back in the good ol' VB 6.0 and C++ days, it was common practice to create a property that was readonly externally and public internally to the application.  This simplified semantics and the programming model was simpler.  However, when I came into .NET I found abruptly that I would have to create a readonly property and then a separate accessor function to set the value of the property internally:

public int Age {
   get { return _age; }
}

internal void setAge(int value) {
   _age = value;
}

I am very excited to learn that in the Whidbey (Visual Studio 5.0) timeframe we'll get scoped property accessors.  Now the syntax would be like the following:

public int Age {
   get { return _age; }
   internal set { _age = value; }
}

As Eric Porter reminds us, this is not just a C# feature, but you'll be able to do the same thing in VB.NET:

Public Property Age() As Integer
   Get
      Return _age
   End Get
   Friend Set(ByVal Value As Integer)
      _age = Value
   End Set
End Property

I can't wait for this enhancement!

Wednesday, June 16, 2004 5:09:00 AM (Mountain Standard Time, UTC-07:00)  #    Disclaimer  |  Comments [0]  |  Trackback

Yesterday I received my new laptop.  It's a new Dell Inspiron 8600.  I must say that so far I am impressed.  It's a blazing Pentium M 755 (2.0 Ghz) with 2GB of RAM.  With the WUXGA (1920x1200 res), 60 GB 7200 RPM hard drive, and the DVD+R/RW I am loving it!  I'm still in the process of setting it up, but I'm very excited.

As a matter of habit, the first thing I do when I get a new computer (PC or otherwise) is blow away the OS (archiving drivers of course) and install anew.  At first I wanted to use Windows Server 2003.  It installed flawlessly; that is, until I got to the video driver.  The video driver installed ok but upon reboot it incessantly blue screened.  It was frustrating to not find a Win2k3-compatible video driver on the Dell site.  I was forced to fall back to Windows XP, which I enjoy as well, but I would have preferred Win2k3...oh well...no worries.

Wednesday, June 16, 2004 3:34:00 AM (Mountain Standard Time, UTC-07:00)  #    Disclaimer  |  Comments [1]  |  Trackback