Compiling to the Common Intermediate Language
Compiling to Native Code and Execution
The Common Language Infrastructure
The C# programming language was designed for developing programs for Microsoft's .NET Framework. This chapter gives a brief look at where .NET came from and its basic architecture. To start off, let's get the name right: C# is pronounced “see sharp.”1
In the late 1990s, Windows programming using the Microsoft platform had fractured into a number of branches. Most programmers were using Visual Basic (VB), C, or C++. Some C and C++ programmers were using the raw Win32 API, but most were using the Microsoft Foundation Classes (MFC). Others had moved to the Component Object Model (COM).
All these technologies had their own problems. The raw Win32 API was not object-oriented, and using it required a lot more work than MFC. MFC was object-oriented but was inconsistent and getting old. COM, although conceptually simple, was complex in its actual coding and required lots of ugly, inelegant plumbing.
Another shortcoming of all these programming technologies was that they were aimed primarily at developing code for the desktop rather than the Internet. At the time, programming for the Web was an afterthought and seemed very different from coding for the desktop.
What we really needed was a new start—an integrated, object-oriented development framework that would bring consistency and elegance back to programming. To meet this need, Microsoft set out to develop a code execution environment and a code development environment that met these goals. Figure 1-1 lists these goals.
Figure 1-1. Goals for the next-generation platform
In 2002, Microsoft released the first version of the .NET Framework, which promised to address the old problems and meet the goals for the next-generation systems. The .NET Framework is a much more consistent and object-oriented environment than either the MFC or COM programming technology. Some of its features include the following:
__________
1 I was once interviewed for a contract C# position when the Human Resources interviewer asked me how much experience I'd had programming in “see pound” (instead of “see sharp”)! It took me a moment to realize what he was talking about.
The .NET Framework consists of three components, as shown in Figure 1-2. The execution environment is called the Common Language Runtime (CLR). The CLR manages program execution at run time, including the following:
The programming tools include everything you need for coding and debugging, including the following:
The Base Class Library (BCL) is a large class library used by the .NET Framework and available for you to use in your programs as well.
Figure 1-2. Components of the .NET Framework
The .NET Framework offers programmers considerable improvements over previous Windows programming environments. The following sections give a brief overview of its features and their benefits.
The CLR, the BCL, and C# are designed to be thoroughly object-oriented and act as a well-integrated environment.
The system provides a consistent, object-oriented model of programming for both local programs and distributed systems. It also provides a software development interface for desktop application programming, mobile application programming, and web development, consistent across a broad range of targets, from servers to cell phones.
The CLR has a service called the garbage collector (GC), which automatically manages memory for you.
The .NET Framework was designed for interoperability between different .NET languages, the operating system or Win32 DLLs, and COM.
The .NET Framework frees the programmer from the COM legacy. As a C# programmer, you don't need to use COM and therefore don't need any of the following:
IUnknown
interface: In COM, all objects must implement interface IUnknown
. In contrast, all .NET objects derive from a single class called object
. Interface programming is still an important part of .NET, but it's no longer the central theme..tlb
files, which are separate from the executable code. In .NET, a program's type information is kept bundled with the code in the program file.HRESULT
: COM used the HRESULT
data type to return runtime error codes. .NET doesn't use HRESULT
s. Instead, all unexpected runtime errors produce exceptions.Although the amount of COM code that's currently being written is fairly small, there's still quite a number of COM components in systems currently being used, and C# programmers sometimes need to write code that interfaces with those components. C# 4.0 introduces several new features that make that task easier.
Deploying programs written for the .NET Framework can be much easier than it was before, for the following reasons:
The CLR checks and ensures the type safety of parameters and other data objects—even between components written in different programming languages.
The .NET Framework supplies an extensive base class library, called, not surprisingly, the Base Class Library (BCL). (It's also sometimes called the Framework Class Library—FCL). You can use this extensive set of available code when writing your own programs. Some of the categories are the following:
The compiler for a .NET language takes a source code file and produces an output file called an assembly. Figure 1-3 illustrates the process.
Figure 1-3. The compilation process
The acronym for the intermediate language has changed over time, and different references use different terms. Two other terms for the CIL that you might encounter are Intermediate Language (IL) and Microsoft Intermediate Language (MSIL). These terms were frequently used during .NET's initial development and early documentation.
The program's CIL isn't compiled to native machine code until it's called to run. At run time, the CLR performs the following steps, as shown in Figure 1-4:
The executable code in the assembly is compiled by the JIT compiler only as it's needed. It's then cached in case it's needed for execution again later in the program. Using this process means that code that isn't called during execution isn't compiled to native code, and code that is called need only be compiled once.
Figure 1-4. Compilation to native code occurs at run time
Once the CIL is compiled to native code, the CLR manages it as it runs, performing such tasks as releasing orphaned memory, checking array bounds, checking parameter types, and managing exceptions. This brings up two important terms:
Microsoft also supplies a tool called the Native Image Generator, or Ngen, which takes an assembly and produces native code for the current processor. Code that's been run through Ngen avoids the JIT compilation process at run time.
The same compilation and execution process is followed regardless of the language of the original source files. Figure 1-5 illustrates the entire compilation and run-time processes for three programs written in different languages.
Figure 1-5. Overview of the compile-time and runtime processes
The core component of the .NET Framework is the CLR, which sits on top of the operating system and manages program execution, as shown in Figure 1-6. The CLR also provides the following services:
Figure 1-6. Overview of the CLR
Every programming language has a set of intrinsic types representing such objects as integers, floating-point numbers, characters, and so on. Historically, the characteristics of these types have varied from one programming language to another and from platform to platform. For example, the number of bits constituting an integer has varied widely depending on the language and platform.
This lack of uniformity, however, makes it difficult if we want programs to play well with other programs and libraries written in different languages. To have order and cooperation, there must be a set of standards.
The Common Language Infrastructure (CLI) is a set of standards that ties all the components of the .NET Framework into a cohesive, consistent system. It lays out the concepts and architecture of the system and specifies the rules and conventions to which all the software must adhere. Figure 1-7 shows the components of the CLI.
Figure 1-7. Components of the CLI
Both the CLI and C# have been approved as open international standard specifications by Ecma International. (The name “Ecma” used to be an acronym for the European Computer Manufacturers Association, but it's now just a word in itself.) Ecma members include Microsoft, IBM, Hewlett-Packard, Adobe, and many other corporations associated with computers and consumer electronics.
Although most programmers don't need to know the details of the CLI specifications, you should at least be familiar with the meaning and purpose of the Common Type System and the Common Language Specification.
The Common Type System (CTS) defines the characteristics of the types that must be used in managed code. Some important aspects of the CTS are the following:
object
.The Common Language Specification (CLS) specifies the rules, properties, and behaviors of a .NET-compliant programming language. The topics include data types, class construction, and parameter passing.
This chapter has covered a lot of .NET acronyms, so Figure 1-8 will help you keep them straight.
Figure 1-8. The .NET acronyms
18.219.239.118