Control.cs source code in C# .NET

Source code for the .NET framework in C#

                        

Code:

/ 4.0 / 4.0 / DEVDIV_TFS / Dev10 / Releases / RTMRel / ndp / fx / src / xsp / System / Web / UI / Control.cs / 1305376 / Control.cs

                            //------------------------------------------------------------------------------ 
// 
//     Copyright (c) Microsoft Corporation.  All rights reserved.
// 
//----------------------------------------------------------------------------- 

namespace System.Web.UI { 
    using System.Text; 
    using System.ComponentModel;
    using System; 
    using System.Collections;
    using System.Collections.Specialized;
    using System.ComponentModel.Design;
    using System.ComponentModel.Design.Serialization; 
    using System.Diagnostics.CodeAnalysis;
    using System.Globalization; 
    using System.Reflection; 
    using System.IO;
    using HttpException = System.Web.HttpException; 
    using System.Web.Configuration;
    using System.Web.UI.Adapters;
    using System.Web.UI.HtmlControls;
    using System.Web.UI.WebControls; 
    using System.Web.Util;
    using System.Web.Hosting; 
    using System.Web.Caching; 
    using System.Web.Routing;
    using System.Security.Permissions; 

    // Delegate used for the compiled template
    public delegate void RenderMethod(HtmlTextWriter output, Control container);
 
    public delegate Control BuildMethod();
 
    // Defines the properties, methods, and events that are shared by all server 
    // controls in the Web Forms page framework.
    [ 
    Bindable(true),
    DefaultProperty("ID"),
    DesignerCategory("Code"),
    Designer("System.Web.UI.Design.ControlDesigner, " + AssemblyRef.SystemDesign), 
    DesignerSerializer("Microsoft.VisualStudio.Web.WebForms.ControlCodeDomSerializer, " + AssemblyRef.MicrosoftVisualStudioWeb,  "System.ComponentModel.Design.Serialization.CodeDomSerializer, " + AssemblyRef.SystemDesign),
    Themeable(false), 
    ToolboxItemFilter("System.Web.UI", ToolboxItemFilterType.Require), 
    ToolboxItemAttribute("System.Web.UI.Design.WebControlToolboxItem, " + AssemblyRef.SystemDesign)
    ] 
    public class Control : IComponent, IParserAccessor, IUrlResolutionService, IDataBindingsAccessor, IControlBuilderAccessor, IControlDesignerAccessor, IExpressionsAccessor {

        internal static readonly object EventDataBinding = new object();
        internal static readonly object EventInit = new object(); 
        internal static readonly object EventLoad = new object();
        internal static readonly object EventUnload = new object(); 
        internal static readonly object EventPreRender = new object(); 
        private static readonly object EventDisposed = new object();
 
        internal const bool EnableViewStateDefault = true;
        internal const char ID_SEPARATOR = '$';
        private const char ID_RENDER_SEPARATOR = '_';
        internal const char LEGACY_ID_SEPARATOR = ':'; 

        private string _id; 
        // allows us to reuse the id variable to store a calculated id w/o polluting the public getter 
        private string _cachedUniqueID;
        private string _cachedPredictableID; 
        private Control _parent;

        // fields related to being a container
        private ControlState _controlState; 
        private StateBag _viewState;
 
        private EventHandlerList _events; 
        private ControlCollection _controls;
 
        // The naming container that this control leaves in.  Note that even if
        // this ctrl is a naming container, it will not point to itself, but to
        // the naming container that contains it.
        private Control _namingContainer; 
        internal Page _page;
        private OccasionalFields _occasionalFields; 
        // The virtual directory of the Page or UserControl that hosts this control. 

        // const masks into the BitVector32 
        private const int idNotCalculated           = 0x00000001;
        private const int marked                    = 0x00000002;
        private const int disableViewState          = 0x00000004;
        private const int controlsCreated           = 0x00000008; 
        private const int invisible                 = 0x00000010;
        private const int visibleDirty              = 0x00000020; 
        private const int idNotRequired             = 0x00000040; 
        private const int isNamingContainer         = 0x00000080;
        private const int creatingControls          = 0x00000100; 
        private const int notVisibleOnPage          = 0x00000200;
        private const int themeApplied              = 0x00000400;
        private const int mustRenderID              = 0x00000800;
        private const int disableTheming            = 0x00001000; 
        private const int enableThemingSet          = 0x00002000;
        private const int styleSheetApplied         = 0x00004000; 
        private const int controlAdapterResolved    = 0x00008000; 
        private const int designMode                = 0x00010000;
        private const int designModeChecked         = 0x00020000; 
        private const int disableChildControlState  = 0x00040000;
        internal const int isWebControlDisabled     = 0x00080000;
        private const int controlStateApplied       = 0x00100000;
        private const int useGeneratedID            = 0x00200000; 
        private const int viewStateNotInherited     = 0x00800000;
        private const int viewStateMode             = 0x01000000; 
        private const int clientIDMode              = 0x06000000; 
        private const int clientIDModeOffset        = 25;
        private const int effectiveClientIDMode     = 0x18000000; 
        private const int effectiveClientIDModeOffset = 27;
        #pragma warning disable 0649
        internal SimpleBitVector32 flags;
        #pragma warning restore 0649 

        private const string automaticIDPrefix = "ctl"; 
        private const string automaticLegacyIDPrefix = "_ctl"; 
        private const int automaticIDCount = 128;
        private static readonly string[] automaticIDs = new string [automaticIDCount] { 
            "ctl00", "ctl01", "ctl02", "ctl03", "ctl04", "ctl05", "ctl06",
            "ctl07", "ctl08", "ctl09", "ctl10", "ctl11", "ctl12", "ctl13",
            "ctl14", "ctl15", "ctl16", "ctl17", "ctl18", "ctl19", "ctl20",
            "ctl21", "ctl22", "ctl23", "ctl24", "ctl25", "ctl26", "ctl27", 
            "ctl28", "ctl29", "ctl30", "ctl31", "ctl32", "ctl33", "ctl34",
            "ctl35", "ctl36", "ctl37", "ctl38", "ctl39", "ctl40", "ctl41", 
            "ctl42", "ctl43", "ctl44", "ctl45", "ctl46", "ctl47", "ctl48", 
            "ctl49", "ctl50", "ctl51", "ctl52", "ctl53", "ctl54", "ctl55",
            "ctl56", "ctl57", "ctl58", "ctl59", "ctl60", "ctl61", "ctl62", 
            "ctl63", "ctl64", "ctl65", "ctl66", "ctl67", "ctl68", "ctl69",
            "ctl70", "ctl71", "ctl72", "ctl73", "ctl74", "ctl75", "ctl76",
            "ctl77", "ctl78", "ctl79", "ctl80", "ctl81", "ctl82", "ctl83",
            "ctl84", "ctl85", "ctl86", "ctl87", "ctl88", "ctl89", "ctl90", 
            "ctl91", "ctl92", "ctl93", "ctl94", "ctl95", "ctl96", "ctl97",
            "ctl98", "ctl99", 
            "ctl100", "ctl101", "ctl102", "ctl103", "ctl104", "ctl105", "ctl106", 
            "ctl107", "ctl108", "ctl109", "ctl110", "ctl111", "ctl112", "ctl113",
            "ctl114", "ctl115", "ctl116", "ctl117", "ctl118", "ctl119", "ctl120", 
            "ctl121", "ctl122", "ctl123", "ctl124", "ctl125", "ctl126", "ctl127"

        };
 
        /// 
        /// Initializes a new instance of the  class. 
        ///  
        [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
        public Control() { 
            if (this is INamingContainer)
                flags.Set(isNamingContainer);
        }
 
        private ClientIDMode ClientIDModeValue {
            get { 
                return (ClientIDMode)flags[clientIDMode, clientIDModeOffset]; 
            }
            set { 
                flags[clientIDMode, clientIDModeOffset] = (int)value;
            }
        }
 
        [SuppressMessage("Microsoft.Naming", "CA1706:ShortAcronymsShouldBeUppercase", MessageId="Member")]
        [ 
        DefaultValue(ClientIDMode.Inherit), 
        Themeable(false),
        WebCategory("Behavior"), 
        WebSysDescription(SR.Control_ClientIDMode)
        ]
        public virtual ClientIDMode ClientIDMode {
            [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")] 
            get {
                return ClientIDModeValue; 
            } 
            set {
                if (ClientIDModeValue != value) { 
                    if (value != EffectiveClientIDModeValue) {
                        ClearEffectiveClientIDMode();
                        ClearCachedClientID();
                    } 
                    ClientIDModeValue = value;
                } 
            } 
        }
 
        private ClientIDMode EffectiveClientIDModeValue {
            get {
                return (ClientIDMode)flags[effectiveClientIDMode, effectiveClientIDModeOffset];
            } 
            set {
                flags[effectiveClientIDMode, effectiveClientIDModeOffset] = (int)value; 
            } 
        }
 
        internal virtual ClientIDMode EffectiveClientIDMode {
            get {
                if (EffectiveClientIDModeValue == ClientIDMode.Inherit) {
                    EffectiveClientIDModeValue = ClientIDMode; 
                    if (EffectiveClientIDModeValue == ClientIDMode.Inherit) {
                        if (NamingContainer != null) { 
                            EffectiveClientIDModeValue = NamingContainer.EffectiveClientIDMode; 
                        }
                        else { 
                            HttpContext context = Context;
                            if (context != null) {
                                EffectiveClientIDModeValue = RuntimeConfig.GetConfig(context).Pages.ClientIDMode;
                            } 
                            else {
                                EffectiveClientIDModeValue = RuntimeConfig.GetConfig().Pages.ClientIDMode; 
                            } 
                        }
                    } 
                }
                return EffectiveClientIDModeValue;
            }
        } 

        internal string UniqueClientID { 
            get { 
                string uniqueID = UniqueID;
                if(uniqueID != null && uniqueID.IndexOf(IdSeparator) >= 0) { 
                    return uniqueID.Replace(IdSeparator, ID_RENDER_SEPARATOR);
                }
                return uniqueID;
            } 
        }
 
        internal string StaticClientID { 
            get {
                return flags[useGeneratedID] ? String.Empty : ID ?? String.Empty; 
            }
        }

        internal ControlAdapter AdapterInternal { 
            get {
                if (_occasionalFields == null || 
                    _occasionalFields.RareFields == null || 
                    _occasionalFields.RareFields.Adapter == null) {
                        return null; 
                }
                return _occasionalFields.RareFields.Adapter;
            }
            set { 
                if (value != null) {
                    RareFieldsEnsured.Adapter = value; 
                } 
                else {
                    if (_occasionalFields != null && 
                        _occasionalFields.RareFields != null &&
                        _occasionalFields.RareFields.Adapter != null) {
                            _occasionalFields.RareFields.Adapter = null;
                    } 
                }
            } 
        } 

        private string GetClientID() { 
            switch (EffectiveClientIDMode) {
                case ClientIDMode.Predictable:
                    return PredictableClientID;
                case ClientIDMode.Static: 
                    return StaticClientID;
                default: 
                    return UniqueClientID; 
            }
        } 

        private string GetPredictableClientIDPrefix() {
            string predictableIDPrefix;
 
            Control namingContainer = NamingContainer;
            if (namingContainer != null) { 
                if (_id == null) { 
                    GenerateAutomaticID();
                } 
                if (namingContainer is Page || namingContainer is MasterPage) {
                    predictableIDPrefix = _id;
                }
                else { 
                    predictableIDPrefix = namingContainer.GetClientID();
                    if (String.IsNullOrEmpty(predictableIDPrefix)) { 
                        predictableIDPrefix = _id; 
                    }
                    else { 
                        if (!String.IsNullOrEmpty(_id) && (!(this is IDataItemContainer) || (this is IDataBoundItemControl))) {
                            predictableIDPrefix = predictableIDPrefix + ID_RENDER_SEPARATOR + _id;
                        }
                    } 
                }
            } 
            else { 
                predictableIDPrefix = _id;
            } 
            return predictableIDPrefix;
        }

        private string GetPredictableClientIDSuffix() { 
            string predictableIDSuffix = null;
 
            Control dataItemContainer = DataItemContainer; 
            if (dataItemContainer != null &&
                !(dataItemContainer is IDataBoundItemControl) && 
                (!(this is IDataItemContainer) || (this is IDataBoundItemControl))) {
                Control dataKeysContainer = dataItemContainer.DataKeysContainer;
                if (dataKeysContainer != null && (((IDataKeysControl)dataKeysContainer).ClientIDRowSuffix != null) && (((IDataKeysControl)dataKeysContainer).ClientIDRowSuffix.Length > 0)) {
                    predictableIDSuffix = String.Empty; 
                    IOrderedDictionary dataKey = ((IDataKeysControl)dataKeysContainer).ClientIDRowSuffixDataKeys[((IDataItemContainer)dataItemContainer).DisplayIndex].Values;
                    foreach (string suffixName in ((IDataKeysControl)dataKeysContainer).ClientIDRowSuffix) { 
                        predictableIDSuffix = predictableIDSuffix + ID_RENDER_SEPARATOR + dataKey[suffixName].ToString(); 
                    }
                } 
                else {
                    int index = ((IDataItemContainer)dataItemContainer).DisplayIndex;
                    if (index >= 0) {
                        predictableIDSuffix = ID_RENDER_SEPARATOR + index.ToString(CultureInfo.InvariantCulture); 
                    }
                } 
            } 
            return predictableIDSuffix;
        } 

        internal string PredictableClientID {
            get {
                if (_cachedPredictableID != null) { 
                    return _cachedPredictableID;
                } 
 
                _cachedPredictableID = GetPredictableClientIDPrefix();
                string suffixID = GetPredictableClientIDSuffix(); 

                // Concatenates Predictable clientID and ClientIDRowSuffix if available
                if (!String.IsNullOrEmpty(suffixID)) {
                    if (!String.IsNullOrEmpty(_cachedPredictableID)) { 
                        _cachedPredictableID = _cachedPredictableID + suffixID;
                    } 
                    else { 
                        _cachedPredictableID = suffixID.Substring(1);
                    } 
                }
                return String.IsNullOrEmpty(_cachedPredictableID) ? String.Empty : _cachedPredictableID;
            }
        } 

        ///  
        ///    Indicates the control identifier generated by the ASP.NET framework.  
        /// 
        [ 
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden),
        WebSysDescription(SR.Control_ClientID)
        ] 
        public virtual string ClientID {
            // This property is required to render a unique client-friendly id. 
            get { 
                if (EffectiveClientIDMode != ClientIDMode.Static) {
                    // Ensure that ID is set. The assumption being made is that the caller 
                    // is likely to use the client ID in script, and to support that the
                    // control should render out an ID attribute
                    EnsureID();
                } 
                return GetClientID();
            } 
        } 

        protected char ClientIDSeparator { 
            get {
                return ID_RENDER_SEPARATOR;
            }
        } 

        ///  
        ///    [To be supplied.] 
        /// 
        [ 
        WebSysDescription(SR.Control_OnDisposed)
        ]
        public event EventHandler Disposed {
            add { 
                Events.AddHandler(EventDisposed, value);
            } 
            remove { 
                Events.RemoveHandler(EventDisposed, value);
            } 
        }

        /// 
        /// Gets the  object of the current Web request. If 
        ///    the control's context is , this will be the context of the
        ///    control's parent, unless the parent control's context is . 
        ///    If this is the case, this will be equal to the HttpContext property. 
        /// 
        [ 
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)
        ]
        protected internal virtual HttpContext Context { 
            //  Request context containing the intrinsics
            [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")] 
            get { 
                Page page = Page;
                if(page != null) { 
                    return page.Context;
                }
                return HttpContext.Current;
            } 
        }
 
        protected virtual ControlAdapter ResolveAdapter() { 
            if(flags[controlAdapterResolved]) {
                return AdapterInternal; 
            }
            if (DesignMode) {
                flags.Set(controlAdapterResolved);
                return null; 
            }
 
            HttpContext context = Context; 
            if (context != null && context.Request.Browser != null) {
                AdapterInternal = context.Request.Browser.GetAdapter(this); 
            }
            flags.Set(controlAdapterResolved);
            return AdapterInternal;
        } 

        ///  
        ///    Indicates the list of event handler delegates for the control. This property 
        ///       is read-only.
        ///  
        protected ControlAdapter Adapter {
            get {
                if(flags[controlAdapterResolved]) {
                    return AdapterInternal; 
                }
                AdapterInternal = ResolveAdapter(); 
                flags.Set(controlAdapterResolved); 
                return AdapterInternal;
            } 
        }

        /// 
        /// Indicates whether a control is being used in the context of a design surface. 
        /// 
        protected internal bool DesignMode { 
            get { 
                if(!flags[designModeChecked]) {
                    Page page = Page; 
                    if(page != null )  {
                        if(page.GetDesignModeInternal()) {
                            flags.Set(designMode);
                        } 
                        else {
                            flags.Clear(designMode); 
                        } 
                    }
                    else { 
                        if(Site != null) {
                            if(Site.DesignMode) {
                                flags.Set(designMode);
                            } 
                            else {
                                flags.Clear(designMode); 
                            } 
                        }
                        else if (Parent != null) { 
                            if(Parent.DesignMode) {
                                flags.Set(designMode);
                            }
 
                            // VSWhidbey 535747: If Page, Site and Parent are all null, do not change the
                            // designMode flag since it might had been previously set by the controlBuilder. 
                            // This does not affect runtime since designMode is by-default false. 
                            /*
                            else { 
                                flags.Clear(designMode);
                            }
                            */
                        } 
                    }
                    flags.Set(designModeChecked); 
                } 
                return flags[designMode];
 
            }
        }

        // Helper function to call validateEvent. 
        internal void ValidateEvent(string uniqueID) {
            ValidateEvent(uniqueID, String.Empty); 
        } 

        // Helper function to call validateEvent. 
        internal void ValidateEvent(string uniqueID, string eventArgument) {
            if (Page != null && SupportsEventValidation) {
                Page.ClientScript.ValidateEvent(uniqueID, eventArgument);
            } 
        }
 
        // Indicates whether the control supports event validation 
        // By default, all web controls in System.Web assembly supports it but not custom controls.
        private bool SupportsEventValidation { 
            get {
                return SupportsEventValidationAttribute.SupportsEventValidation(this.GetType());
            }
        } 

        ///  
        ///    Indicates the list of event handler delegates for the control. This property 
        ///       is read-only.
        ///  
        protected EventHandlerList Events {
            [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
            get {
                if (_events == null) { 
                    _events = new EventHandlerList();
                } 
                return _events; 
            }
        } 

        [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
        protected bool HasEvents() {
            return (_events != null); 
        }
 
        ///  
        ///     Gets or sets the identifier for the control. Setting the
        ///       property on a control allows programmatic access to the control's properties. If 
        ///       this property is not specified on a control, either declaratively or
        ///       programmatically, then you cannot write event handlers and the like for the control.
        /// 
        [ 
        ParenthesizePropertyName(true),
        MergableProperty(false), 
        Filterable(false), 
        Themeable(false),
        WebSysDescription(SR.Control_ID) 
        ]
        public virtual string ID {
            get {
                if (!flags[idNotCalculated] && !flags[mustRenderID]) { 
                    return null;
                } 
                return _id; 
            }
            set { 
                // allow the id to be unset
                if (value != null && value.Length == 0)
                    value = null;
 
                string oldID = _id;
 
                _id = value; 
                ClearCachedUniqueIDRecursive();
                flags.Set(idNotCalculated); 
                flags.Clear(useGeneratedID);

                // Update the ID in the naming container
                if ((_namingContainer != null) && (oldID != null)) { 
                    _namingContainer.DirtyNameTable();
                } 
 
                if (oldID != null && oldID != _id) {
                    ClearCachedClientID(); 
                }
            }
        }
 

        ///  
        ///    Gets and sets a value indicating whether theme is enabled. 
        /// 
        [ 
        Browsable(false),
        DefaultValue(true),
        Themeable(false),
        WebCategory("Behavior"), 
        WebSysDescription(SR.Control_EnableTheming)
        ] 
        public virtual bool EnableTheming { 
            get {
                if (flags[enableThemingSet]) { 
                    return !flags[disableTheming];
                }

                if (Parent != null) { 
                    return Parent.EnableTheming;
                } 
 
                return !flags[disableTheming];
            } 
            set {
                if ((_controlState >= ControlState.FrameworkInitialized) && !DesignMode) {
                    throw new InvalidOperationException(SR.GetString(SR.PropertySetBeforePreInitOrAddToControls, "EnableTheming"));
                } 

                if(!value) { 
                    flags.Set(disableTheming); 
                }
                else { 
                    flags.Clear(disableTheming);
                }

                flags.Set(enableThemingSet); 
            }
        } 
 
        // Serialzie the value if it's set explicitely.
        internal bool ShouldSerializeEnableTheming() { 
            return flags[enableThemingSet];;
        }

        internal bool IsBindingContainer { 
            get {
                return this is INamingContainer && !(this is INonBindingContainer); 
            } 
        }
 
        protected internal bool IsChildControlStateCleared {
            get {
                return flags[disableChildControlState];
            } 
        }
 
 
        /// 
        ///    Gets and sets the skinID of the control. 
        /// 
        [
        Browsable(false),
        DefaultValue(""), 
        Filterable(false),
        WebCategory("Behavior"), 
        WebSysDescription(SR.Control_SkinId), 
        ]
        public virtual string SkinID { 
            get {
                if(_occasionalFields != null) {
                    return _occasionalFields.SkinId == null ? String.Empty : _occasionalFields.SkinId;
                } 
                return String.Empty;
            } 
            set { 
                if (!DesignMode) {
                    if (flags[styleSheetApplied]) { 
                        throw new InvalidOperationException(SR.GetString(SR.PropertySetBeforeStyleSheetApplied, "SkinId"));
                    }

                    if (_controlState >= ControlState.FrameworkInitialized) { 
                        throw new InvalidOperationException(SR.GetString(SR.PropertySetBeforePreInitOrAddToControls, "SkinId"));
                    } 
                } 

                EnsureOccasionalFields(); 
                _occasionalFields.SkinId = value;
            }
        }
 
        private ControlRareFields RareFieldsEnsured {
            get { 
                EnsureOccasionalFields(); 
                ControlRareFields rareFields = _occasionalFields.RareFields;
                if(rareFields == null) { 
                    rareFields = new ControlRareFields();
                    _occasionalFields.RareFields = rareFields;
                }
 
                return rareFields;
            } 
        } 

        private ControlRareFields RareFields { 
            get {
                if(_occasionalFields != null) {
                    return _occasionalFields.RareFields;
                } 
                return null;
            } 
        } 

        private void EnsureOccasionalFields() { 
            if(_occasionalFields == null) {
                _occasionalFields = new OccasionalFields();
            }
        } 

 
        ///  
        ///    
        ///       Gets or sets a value indicating whether the control should maintain its view 
        ///       state, and the view state of any child control in contains, when the current
        ///       page request ends.
        ///    
        ///  
        [
        DefaultValue(EnableViewStateDefault), 
        Themeable(false), 
        WebCategory("Behavior"),
        WebSysDescription(SR.Control_MaintainState) 
        ]
        public virtual bool EnableViewState {
            get {
                return !flags[disableViewState]; 
            }
            set { 
                SetEnableViewStateInternal(value); 
            }
        } 

        [
        DefaultValue(ViewStateMode.Inherit),
        Themeable(false), 
        WebCategory("Behavior"),
        WebSysDescription(SR.Control_ViewStateMode) 
        ] 
        public virtual ViewStateMode ViewStateMode {
            get { 
                return flags[viewStateNotInherited] ?
                    (flags[viewStateMode] ? ViewStateMode.Enabled : ViewStateMode.Disabled) :
                    ViewStateMode.Inherit;
            } 
            set {
                if ((value < ViewStateMode.Inherit) || (value > ViewStateMode.Disabled)) { 
                    throw new ArgumentOutOfRangeException("value"); 
                }
                if (value == ViewStateMode.Inherit) { 
                    flags.Clear(viewStateNotInherited);
                }
                else {
                    flags.Set(viewStateNotInherited); 
                    if (value == ViewStateMode.Enabled) {
                        flags.Set(viewStateMode); 
                    } 
                    else {
                        flags.Clear(viewStateMode); 
                    }
                }
            }
        } 

 
        internal void SetEnableViewStateInternal(bool value) { 
            if (!value)
                flags.Set(disableViewState); 
            else
                flags.Clear(disableViewState);
        }
 

        ///  
        /// Gets a value indicating whether the control is maintaining its view 
        /// state, when the current page request ends by looking at its own EnableViewState
        /// value, and the value for all its parents. 
        /// 
        protected internal bool IsViewStateEnabled {
            get {
                Control current = this; 
                while (current != null) {
                    if (current.EnableViewState == false) { 
                        return false; 
                    }
                    ViewStateMode mode = current.ViewStateMode; 
                    if (mode != ViewStateMode.Inherit) {
                        return (mode == ViewStateMode.Enabled);
                    }
                    current = current.Parent; 
                }
                return true; 
            } 
        }
 

        /// 
        ///    Gets the reference to the current control's naming container.
        ///  
        [
        Bindable(false), 
        Browsable(false), 
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden),
        WebSysDescription(SR.Control_NamingContainer) 
        ]
        public virtual Control NamingContainer {
            get {
                if (_namingContainer == null) { 
                    if (Parent != null) {
                        // Search for the closest naming container in the tree 
                        if (Parent.flags[isNamingContainer]) 
                            _namingContainer = Parent;
                        else 
                            _namingContainer = Parent.NamingContainer;
                    }
                }
 
                return _namingContainer;
            } 
        } 

        ///  
        /// 
        ///    Returns the databinding container of this control.  In most cases,
        ///     this is the same as the NamingContainer. But when using LoadTemplate(),
        ///     we get into a situation where that is not the case (ASURT 94138) 
        ///     The behavior is different than V1 that Usercontrol.BindingContainer is no
        ///     longer the UserControl but the control contains it. The behavior is consistent 
        ///     with LoadTemplate() case. 
        /// 
        [ 
        Bindable(false),
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden),
        EditorBrowsable(EditorBrowsableState.Never) 
        ]
        public Control BindingContainer { 
            get { 
                Control bindingContainer = NamingContainer;
                while (bindingContainer is INonBindingContainer) { 
                    bindingContainer = bindingContainer.BindingContainer;
                }

                return bindingContainer; 
            }
        } 
 
        [
        Bindable(false), 
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden),
        EditorBrowsable(EditorBrowsableState.Never)
        ] 
        public Control DataItemContainer {
            get { 
                Control dataItemContainer = NamingContainer; 
                while (dataItemContainer != null && !(dataItemContainer is IDataItemContainer)) {
                    dataItemContainer = dataItemContainer.DataItemContainer; 
                }

                return dataItemContainer;
            } 
        }
 
        [ 
        Bindable(false),
        Browsable(false), 
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden),
        EditorBrowsable(EditorBrowsableState.Never)
        ]
        public Control DataKeysContainer { 
            get {
                Control dataKeysContainer = NamingContainer; 
                while (dataKeysContainer != null && !(dataKeysContainer is IDataKeysControl)) { 
                    dataKeysContainer = dataKeysContainer.DataKeysContainer;
                } 

                return dataKeysContainer;
            }
        } 

 
 
        /// 
        ///  
        /// VSWhidbey 80467: Need to adapt id separator.
        /// 
        protected char IdSeparator {
            [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")] 
            get {
                if (Page != null) { 
                    return Page.IdSeparator; 
                }
                return IdSeparatorFromConfig; 
            }
        }

        // VSWhidbey 475945: Use the old id separator if configured 
        internal char IdSeparatorFromConfig {
            get { 
                return ((EnableLegacyRendering) ? LEGACY_ID_SEPARATOR : ID_SEPARATOR); 
            }
        } 

        // VSWhidbey 244374: Allow controls to opt into loading view state by ID instead of index (perf hit)
        protected bool LoadViewStateByID {
            get { 
                return ViewStateModeByIdAttribute.IsEnabled(GetType());
            } 
        } 

        ///  
        ///  Gets the  object that contains the
        ///    current control.
        /// 
        [ 
        Bindable(false),
        Browsable(false), 
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), 
        WebSysDescription(SR.Control_Page)
        ] 
        public virtual Page Page {
            get {
                if (_page == null) {
                    if (Parent != null) { 
                        _page = Parent.Page;
                    } 
                } 
                return _page;
            } 

            set {
                if (OwnerControl != null) {
                    throw new InvalidOperationException(); 
                }
                // This is necessary because we need to set the page in generated 
                // code before controls are added to the tree (ASURT 75330) 
                Debug.Assert(_page == null);
                Debug.Assert(Parent == null || Parent.Page == null); 
                _page = value;
            }
        }
 
        internal RouteCollection RouteCollection {
            get { 
                if (_occasionalFields == null || 
                    _occasionalFields.RareFields == null ||
                    _occasionalFields.RareFields.RouteCollection == null) { 
                        return RouteTable.Routes;
                }
                return _occasionalFields.RareFields.RouteCollection;
            } 
            set {
                if (value != null) { 
                    RareFieldsEnsured.RouteCollection = value; 
                }
                else { 
                    if (_occasionalFields != null &&
                        _occasionalFields.RareFields != null &&
                        _occasionalFields.RareFields.RouteCollection != null) {
                            _occasionalFields.RareFields.RouteCollection = null; 
                    }
                } 
            } 
        }
 
        // VSWhidbey 244999
        internal virtual bool IsReloadable {
            [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
            get { 
                return false;
            } 
        } 

        // DevDiv 33149, 43258: A backward compat. switch for Everett rendering 
        internal bool EnableLegacyRendering {
            get {
                Page page = Page;
                if (page != null) { 
                    return (page.XhtmlConformanceMode == XhtmlConformanceMode.Legacy);
                } 
                else if (DesignMode || Adapter != null) { 
                    return false;
                } 
                else {
                    return (GetXhtmlConformanceSection().Mode == XhtmlConformanceMode.Legacy);
                }
            } 
        }
 
        internal XhtmlConformanceSection GetXhtmlConformanceSection() { 
            HttpContext context = Context;
            XhtmlConformanceSection xhtmlConformanceSection; 
            if (context != null) {
                // if context is available, use the most efficient way to get the section
                xhtmlConformanceSection = RuntimeConfig.GetConfig(context).XhtmlConformance;
            } 
            else {
                xhtmlConformanceSection = RuntimeConfig.GetConfig().XhtmlConformance; 
            } 
            Debug.Assert(xhtmlConformanceSection != null);
            return xhtmlConformanceSection; 
        }

        [
        Bindable(false), 
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), 
        ] 
        public virtual Version RenderingCompatibility {
            get { 
                if (_occasionalFields == null ||
                    _occasionalFields.RareFields == null ||
                    _occasionalFields.RareFields.RenderingCompatibility == null) {
                        return RuntimeConfig.Pages.ControlRenderingCompatibilityVersion; 
                }
                return _occasionalFields.RareFields.RenderingCompatibility; 
            } 
            set {
                if (value != null) { 
                    RareFieldsEnsured.RenderingCompatibility = value;
                }
                else {
                    if (_occasionalFields != null && 
                        _occasionalFields.RareFields != null &&
                        _occasionalFields.RareFields.RenderingCompatibility != null) { 
                            _occasionalFields.RareFields.RenderingCompatibility = null; 
                    }
                } 
            }
        }

        private RuntimeConfig RuntimeConfig { 
            get {
                HttpContext context = Context; 
                if (context != null) { 
                    // if context is available, use the most efficient way to get the config
                    return RuntimeConfig.GetConfig(context); 
                } else {
                    return RuntimeConfig.GetConfig();
                }
            } 
        }
 
        [SuppressMessage("Microsoft.Design", "CA1055:UriReturnValuesShouldNotBeStrings", 
            Justification = "Consistent with other URL properties in ASP.NET.")]
        public string GetRouteUrl(object routeParameters) { 
            return GetRouteUrl(new RouteValueDictionary(routeParameters));
        }

        [SuppressMessage("Microsoft.Design", "CA1055:UriReturnValuesShouldNotBeStrings", 
            Justification = "Consistent with other URL properties in ASP.NET.")]
        public string GetRouteUrl(string routeName, object routeParameters) { 
            return GetRouteUrl(routeName, new RouteValueDictionary(routeParameters)); 
        }
 
        [SuppressMessage("Microsoft.Design", "CA1055:UriReturnValuesShouldNotBeStrings",
            Justification = "Consistent with other URL properties in ASP.NET.")]
        public string GetRouteUrl(RouteValueDictionary routeParameters) {
            return GetRouteUrl(null, routeParameters); 
        }
 
        [SuppressMessage("Microsoft.Design", "CA1055:UriReturnValuesShouldNotBeStrings", 
            Justification = "Consistent with other URL properties in ASP.NET.")]
        public string GetRouteUrl(string routeName, RouteValueDictionary routeParameters) { 
            VirtualPathData data = RouteCollection.GetVirtualPath(Context.Request.RequestContext, routeName, routeParameters);
            if (data != null) {
                return data.VirtualPath;
            } 
            return null;
        } 
 
        /// 
        ///    Gets the reference to the  
        ///    that hosts the control.
        /// 
        internal virtual TemplateControl GetTemplateControl() {
            if (_occasionalFields == null || _occasionalFields.TemplateControl == null) { 
                if (Parent != null) {
                    TemplateControl templateControl = Parent.GetTemplateControl(); 
                    if (templateControl != null) { 
                        EnsureOccasionalFields();
                        _occasionalFields.TemplateControl = templateControl; 
                    }
                }
            }
            return (_occasionalFields != null) ? _occasionalFields.TemplateControl : null; 
        }
 
 
        /// 
        ///    Gets the reference to the  
        ///    that hosts the control.
        /// 
        [
        Bindable(false), 
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), 
        WebSysDescription(SR.Control_TemplateControl) 
        ]
        public TemplateControl TemplateControl { 
            get {
                return GetTemplateControl();
            }
 
            [EditorBrowsable(EditorBrowsableState.Never)]
            set { 
                // This setter is necessary so that controls inside templates are based on 
                // hosting pages not where the templates are used.
                if (value != null) { 
                    EnsureOccasionalFields();
                    _occasionalFields.TemplateControl = value;
                }
                else { 
                    if (_occasionalFields != null &&
                        _occasionalFields.TemplateControl != null) { 
                            _occasionalFields.TemplateControl = null; 
                    }
                } 
            }
        }

        /* 
         * Determine whether this control is a descendent of the passed in control
         */ 
        internal bool IsDescendentOf(Control ancestor) { 
            Control current = this;
            while (current != ancestor && current.Parent != null) { 
                current = current.Parent;
            }
            return (current == ancestor);
        } 

 
        ///  
        ///     Gets the current control's parent control in the UI hierarchy.
        ///  
        [
        Bindable(false),
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), 
        WebSysDescription(SR.Control_Parent)
        ] 
        public virtual Control Parent { 
            [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
            get { 
                return _parent;
            }
        }
 
        internal bool IsParentedToUpdatePanel {
            get { 
                Control parent = Parent; 
                while (parent != null) {
                    if (parent is IUpdatePanel) { 
                        return true;
                    }
                    parent = parent.Parent;
                } 
                return false;
            } 
        } 

        ///  
        ///     Gets the virtual directory of the Page or UserControl that contains this control.
        /// 
        [
        Browsable(false), 
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden),
        WebSysDescription(SR.Control_TemplateSourceDirectory) 
        ] 
        public virtual string TemplateSourceDirectory {
            get { 
                if (TemplateControlVirtualDirectory == null)
                    return String.Empty;

                return TemplateControlVirtualDirectory.VirtualPathStringNoTrailingSlash; 
            }
        } 
 

        ///  
        ///     Gets the virtual directory of the Page or UserControl that contains this control.
        ///         Unlike TemplateSourceDirectory, this returns an app relative path (e.g. "~/sub")
        /// 
        [ 
        Browsable(false),
        EditorBrowsable(EditorBrowsableState.Advanced), 
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), 
        WebSysDescription(SR.Control_TemplateSourceDirectory)
        ] 
        public string AppRelativeTemplateSourceDirectory {
            get {
                return VirtualPath.GetAppRelativeVirtualPathStringOrEmpty(TemplateControlVirtualDirectory);
            } 

            [EditorBrowsable(EditorBrowsableState.Never)] 
            set { 
                // This setter is necessary so that skins are based on hosting skin file.
                this.TemplateControlVirtualDirectory = VirtualPath.CreateNonRelativeAllowNull(value); 
            }
        }

        internal VirtualPath TemplateControlVirtualDirectory { 
            get {
                if (_occasionalFields != null && _occasionalFields.TemplateSourceVirtualDirectory != null) 
                    return _occasionalFields.TemplateSourceVirtualDirectory; 

                TemplateControl control = TemplateControl; 
                if (control == null) {
                    HttpContext context = Context;
                    if (context != null) {
                        VirtualPath templateSourceVirtualDirectory = context.Request.CurrentExecutionFilePathObject.Parent; 
                        if (templateSourceVirtualDirectory != null) {
                            EnsureOccasionalFields(); 
                            _occasionalFields.TemplateSourceVirtualDirectory = templateSourceVirtualDirectory; 
                        }
                    } 
                    return (_occasionalFields != null) ? _occasionalFields.TemplateSourceVirtualDirectory : null;
                }
                // Prevent recursion if this is the TemplateControl
                if (control != this) { 
                    VirtualPath templateSourceVirtualDirectory = control.TemplateControlVirtualDirectory;
                    if (templateSourceVirtualDirectory != null) { 
                        EnsureOccasionalFields(); 
                        _occasionalFields.TemplateSourceVirtualDirectory = templateSourceVirtualDirectory;
                    } 
                }
                return (_occasionalFields != null) ? _occasionalFields.TemplateSourceVirtualDirectory : null;
            }
 
            set {
                // This setter is necessary so that skins are based on hosting skin file. 
                if (value != null) { 
                    EnsureOccasionalFields();
                    _occasionalFields.TemplateSourceVirtualDirectory = value; 
                }
                else {
                    if (_occasionalFields != null &&
                        _occasionalFields.TemplateSourceVirtualDirectory != null) { 
                            _occasionalFields.TemplateSourceVirtualDirectory = null;
                    } 
                } 
            }
        } 

        internal ControlState ControlState {
            get { return _controlState; }
            set { _controlState = value; } 
        }
 
 
        /// 
        ///    Indicates the site information for the control. 
        /// 
        [
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), 
        EditorBrowsable(EditorBrowsableState.Advanced),
        WebSysDescription(SR.Control_Site) 
        ] 
        public ISite Site {
            get { 
                if (OwnerControl != null) {
                    return OwnerControl.Site;
                }
 
                if (RareFields != null) {
                    return RareFields.Site; 
                } 
                return null;
            } 
            set {
                if (OwnerControl != null) {
                    throw new InvalidOperationException(SR.GetString(SR.Substitution_SiteNotAllowed));
                } 

                RareFieldsEnsured.Site = value; 
                flags.Clear(designModeChecked); 
            }
        } 


        /// 
        ///     
        ///       Gets or sets a value that indicates whether a control should be rendered on
        ///       the page. 
        ///     
        /// 
        [ 
        Bindable(true),
        DefaultValue(true),
        WebCategory("Behavior"),
        WebSysDescription(SR.Control_Visible) 
        ]
        public virtual bool Visible { 
            get { 
                if (flags[invisible])
                    return false; 
                else if ((_parent != null) && !DesignMode)
                    return _parent.Visible;
                else
                    return true; 
            }
            set { 
                if (flags[marked]) { 
                    bool visible = !flags[invisible];
                    if (visible != value) { 
                        flags.Set(visibleDirty);
                    }
                }
 
                if(!value) {
                    flags.Set(invisible); 
                } 
                else {
                    flags.Clear(invisible); 
                }
            }
        }
 

        ///  
        /// Do not remove or change the signature. It is called via reflection. 
        /// This allows for correct serialization, since Visible is implemented as a
        /// recursive property. 
        /// 
        private void ResetVisible() {
            Visible = true;
        } 

 
        ///  
        /// Do not remove or change the signature. It is called via reflection.
        /// This allows for correct serialization, since Visible is implemented as a 
        /// recursive property.
        /// 
        private bool ShouldSerializeVisible() {
            return flags[invisible]; 
        }
 
 
        /// 
        ///     Gets the unique, hierarchically-qualified identifier for 
        ///       a control. This is different from the ID property, in that the fully-qualified
        ///       identifier includes the identifier for the control's naming container.
        /// 
        [ 
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), 
        WebSysDescription(SR.Control_UniqueID) 
        ]
        public virtual string UniqueID { 
            get {
                if (_cachedUniqueID != null) {
                    return _cachedUniqueID;
                } 

                Control namingContainer = NamingContainer; 
                if (namingContainer != null) { 
                    // if the ID is null at this point, we need to have one created and the control added to the
                    // naming container. 
                    if (_id == null) {
                        GenerateAutomaticID();
                    }
 
                    if (Page == namingContainer) {
                        _cachedUniqueID = _id; 
                    } 
                    else {
                        string uniqueIDPrefix = namingContainer.GetUniqueIDPrefix(); 
                        if (uniqueIDPrefix.Length == 0) {
                            // In this case, it is probably a naming container that is not sited, so we don't want to cache it
                            return _id;
                        } 
                        else {
                            _cachedUniqueID = uniqueIDPrefix + _id; 
                        } 
                    }
 
                    return _cachedUniqueID;
                }
                else {
                    // no naming container 
                    return _id;
                } 
            } 
        }
 
        [SuppressMessage("Microsoft.Naming", "CA1709:IdentifiersShouldBeCasedCorrectly", MessageId = "ID", Justification="This is consistent with UniqueID")]
        [SuppressMessage("Microsoft.Naming", "CA1706:ShortAcronymsShouldBeUppercase", MessageId = "Member", Justification="This is consistent with UniqueID")]
        public string GetUniqueIDRelativeTo(Control control) {
            if (control == null) { 
                throw new ArgumentNullException("control");
            } 
 
            if (!IsDescendentOf(control.NamingContainer)) {
                throw new InvalidOperationException(SR.GetString(SR.Control_NotADescendentOfNamingContainer, control.ID)); 
            }

            if (control.NamingContainer == Page) {
                return UniqueID; 
            } else {
                return UniqueID.Substring(control.NamingContainer.UniqueID.Length + 1); // add 1 for the ID seperator (which is a char) 
            } 
        }
 
        /// 
        ///    Occurs when the control binds to a data source. Notifies the control to perform any data binding during this event.
        /// 
        [ 
        WebCategory("Data"),
        WebSysDescription(SR.Control_OnDataBind) 
        ] 
        public event EventHandler DataBinding {
            add { 
                Events.AddHandler(EventDataBinding, value);
            }
            remove {
                Events.RemoveHandler(EventDataBinding, value); 
            }
        } 
 

        ///  
        ///    Occurs when the control is initialized, the first step in the page lifecycle. Controls should
        ///       perform any initialization steps that are required to create and set up an
        ///       instantiation.
        ///  
        [
        WebSysDescription(SR.Control_OnInit) 
        ] 
        public event EventHandler Init {
            add { 
                Events.AddHandler(EventInit, value);
            }
            remove {
                Events.RemoveHandler(EventInit, value); 
            }
        } 
 

        ///  
        /// Occurs when the control is loaded to the  object. Notifies the control to perform any steps that
        ///    need to occur on each page request.
        /// 
        [ 
        WebSysDescription(SR.Control_OnLoad)
        ] 
        public event EventHandler Load { 
            add {
                Events.AddHandler(EventLoad, value); 
            }
            remove {
                Events.RemoveHandler(EventLoad, value);
            } 
        }
 
 
        /// 
        ///    Occurs when the control is about to render. Controls 
        ///       should perform any pre-rendering steps necessary before saving view state and
        ///       rendering content to the  object.
        /// 
        [ 
        WebSysDescription(SR.Control_OnPreRender)
        ] 
        public event EventHandler PreRender { 
            add {
                Events.AddHandler(EventPreRender, value); 
            }
            remove {
                Events.RemoveHandler(EventPreRender, value);
            } 
        }
 
 
        /// 
        ///    Occurs when the control is unloaded from memory. Controls should perform any 
        ///       final cleanup before this instance of it is 
        /// 
        [
        WebSysDescription(SR.Control_OnUnload) 
        ]
        public event EventHandler Unload { 
            add { 
                Events.AddHandler(EventUnload, value);
            } 
            remove {
                Events.RemoveHandler(EventUnload, value);
            }
        } 

        ///  
        /// Apply stylesheet skin on the control. 
        /// 
        [ 
        EditorBrowsable(EditorBrowsableState.Advanced),
        ]
        public virtual void ApplyStyleSheetSkin(Page page) {
            // Nothing to do if the control is not in a Page. 
            if (page == null) {
                return; 
            } 

            // Only apply stylesheet if not already applied. 
            if (flags[styleSheetApplied]) {
                throw new InvalidOperationException(SR.GetString(SR.StyleSheetAreadyAppliedOnControl));
            }
 
            if (page.ApplyControlStyleSheet(this)) {
                flags.Set(styleSheetApplied); 
            } 
        }
 
        /// 
        /// Apply theme on the control.
        /// 
        private void ApplySkin(Page page) { 
            if (page == null) {
                throw new ArgumentNullException("page"); 
            } 

            if (flags[themeApplied]) { 
                return;
            }

            if (ThemeableAttribute.IsTypeThemeable(this.GetType())) { 
                page.ApplyControlSkin(this);
                flags.Set(themeApplied); 
            } 
        }
 

        /// 
        /// Raises the  event. This
        ///    notifies a control to perform any data binding logic that is associated with it. 
        /// 
        protected virtual void OnDataBinding(EventArgs e) { 
            if(HasEvents()) { 
                EventHandler handler = _events[EventDataBinding] as EventHandler;
                if(handler != null) { 
                    handler(this, e);
                }
            }
        } 

 
        ///  
        ///     Causes data binding to occur on the invoked control and all of its child
        ///       controls. 
        /// 
        public virtual void DataBind() {
            DataBind(true);
        } 

        ///  
        ///     Causes the invoked controls' context to be pushed on the stack, 
        ///       then conditionally call OnDataBinging on the invoked control, and databind all of its child
        ///       controls.  A control would call this with false if it overrides DataBind without calling 
        ///       Control.DataBind, but still wants to be an IDataItemContainer.  FormView and DetailsView
        ///       are good examples of this.
        /// 
        protected virtual void DataBind(bool raiseOnDataBinding) { 
            bool inDataBind = false;
 
            if (IsBindingContainer) { 
                bool foundDataItem;
 
                object dataItem = DataBinder.GetDataItem(this, out foundDataItem);

                if (foundDataItem && (Page != null)) {
                    Page.PushDataBindingContext(dataItem); 
                    inDataBind = true;
                } 
            } 
            try {
                if (raiseOnDataBinding) { 
                    // Do our own databinding
                    OnDataBinding(EventArgs.Empty);
                }
 
                // Do all of our children's databinding
                DataBindChildren(); 
            } 
            finally {
                if (inDataBind) { 
                    Page.PopDataBindingContext();
                }
            }
        } 

 
        ///  
        ///  Causes data binding to occur on all of the child controls.
        ///  
        protected virtual void DataBindChildren() {
            if (HasControls()) {
                string oldmsg = _controls.SetCollectionReadOnly(SR.Parent_collections_readonly);
 
                try {
                    try { 
                        int controlCount = _controls.Count; 
                        for (int i=0; i < controlCount; i++)
                            _controls[i].DataBind(); 
                    }
                    finally {
                        _controls.SetCollectionReadOnly(oldmsg);
                    } 
                }
                catch { 
                    throw; 
                }
            } 
        }

        [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
        internal void PreventAutoID() { 
            // controls that are also naming containers must always get an id
            if (flags[isNamingContainer] == false) { 
                flags.Set(idNotRequired); 
            }
        } 


        /// 
        ///    Notifies the control that an element, XML or HTML, was parsed, and adds it to 
        ///       the control.
        ///  
        [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")] 
        protected virtual void AddParsedSubObject(object obj) {
            Control control = obj as Control; 
            if (control != null) {
                Controls.Add(control);
            }
        } 

        private void UpdateNamingContainer(Control namingContainer) { 
            // Remove the cached uniqueID if the control already had a namingcontainer 
            // and the namingcontainer is changed.
            if (_namingContainer == null || (_namingContainer != null && _namingContainer != namingContainer)) { 
                ClearCachedUniqueIDRecursive();
            }

            // No need to clear the cache if never been initialized 
            if (EffectiveClientIDModeValue != ClientIDMode.Inherit) {
                ClearCachedClientID(); 
                ClearEffectiveClientIDMode(); 
            }
 
            _namingContainer = namingContainer;
        }

        private void ClearCachedUniqueIDRecursive() { 
            _cachedUniqueID = null;
 
            if (_occasionalFields != null) { 
                _occasionalFields.UniqueIDPrefix = null;
            } 

            if (_controls != null) {
                int controlCount = _controls.Count;
                for (int i = 0; i < controlCount; i++) { 
                    _controls[i].ClearCachedUniqueIDRecursive();
                } 
            } 
        }
 
        protected void EnsureID() {
            if (_namingContainer != null) {
                if (_id == null) {
                    GenerateAutomaticID(); 
                }
                flags.Set(mustRenderID); 
            } 
        }
 
        private void GenerateAutomaticID() {
            Debug.Assert(_namingContainer != null);
            Debug.Assert(_id == null);
 
            // Remember that a generated ID is used for this control.
            flags.Set(useGeneratedID); 
 
            // Calculate the automatic ID. For performance and memory reasons
            // we look up a static table entry if possible 
            _namingContainer.EnsureOccasionalFields();
            int idNo = _namingContainer._occasionalFields.NamedControlsID++;
            if (EnableLegacyRendering) {
                // VSWhidbey 517118 
                _id = automaticLegacyIDPrefix + idNo.ToString(NumberFormatInfo.InvariantInfo);
            } 
            else { 
                if (idNo < automaticIDCount) {
                    _id = automaticIDs[idNo]; 
                }
                else {
                    _id = automaticIDPrefix + idNo.ToString(NumberFormatInfo.InvariantInfo);
                } 
            }
 
            _namingContainer.DirtyNameTable(); 
        }
 
        internal virtual string GetUniqueIDPrefix() {
            EnsureOccasionalFields();

            if (_occasionalFields.UniqueIDPrefix == null) { 
                string uniqueID = UniqueID;
                if (!String.IsNullOrEmpty(uniqueID)) { 
                    _occasionalFields.UniqueIDPrefix = uniqueID + IdSeparator; 
                }
                else { 
                    _occasionalFields.UniqueIDPrefix = String.Empty;
                }
            }
 
            return _occasionalFields.UniqueIDPrefix;
        } 
 
        /// 
        /// Raises the  event. This notifies the control to perform 
        ///    any steps necessary for its creation on a page request.
        /// 
        protected internal virtual void OnInit(EventArgs e) {
            if(HasEvents()) { 
                EventHandler handler = _events[EventInit] as EventHandler;
                if(handler != null) { 
                    handler(this, e); 
                }
            } 
        }

        internal virtual void InitRecursive(Control namingContainer) {
            ResolveAdapter(); 
            if (_controls != null) {
                if (flags[isNamingContainer]) { 
                    namingContainer = this; 
                }
                string oldmsg = _controls.SetCollectionReadOnly(SR.Parent_collections_readonly); 

                int controlCount = _controls.Count;
                for (int i = 0; i < controlCount; i++) {
                    Control control = _controls[i]; 

                    // Propagate the page and namingContainer 
                    control.UpdateNamingContainer(namingContainer); 

                    if ((control._id == null) && (namingContainer != null) && !control.flags[idNotRequired]) { 
                        control.GenerateAutomaticID();
                    }
                    control._page = Page;
 
                    control.InitRecursive(namingContainer);
                } 
                _controls.SetCollectionReadOnly(oldmsg); 

            } 

            // Only make the actual call if it hasn't already happened (ASURT 111303)
            if (_controlState < ControlState.Initialized) {
                _controlState = ControlState.ChildrenInitialized; // framework also initialized 

                if ((Page != null) && !DesignMode) { 
                    if (Page.ContainsTheme && EnableTheming) { 
                        ApplySkin(Page);
                    } 
                }

                if (AdapterInternal != null) {
                    AdapterInternal.OnInit(EventArgs.Empty); 
                }
                else { 
                    OnInit(EventArgs.Empty); 
                }
 
                _controlState = ControlState.Initialized;
            }

            // track all subsequent state changes 
            TrackViewState();
 
#if DEBUG 
            ControlInvariant();
#endif 
        }

#if DEBUG
 
        /// 
        ///    This should be used to assert internal state about the control 
        ///  
        internal void ControlInvariant() {
 
            // If the control is initialized, the naming container and page should have been pushed in
            if (_controlState >= ControlState.Initialized) {
                if (DesignMode) {
                    // Top-level UserControls do not have a page or a naming container in the designer 
                    // hence the special casing.
 
                    Debug.Assert((_namingContainer != null) || (this is Page) || (this is UserControl)); 

                    // 



                } 
                else {
                    if (!(this is Page)) { 
                        Debug.Assert(_namingContainer != null); 
                    }
                    Debug.Assert(Page != null); 
                }
            }
            // If naming container is set and the name table exists, the ID should exist in it.
 
            if(_namingContainer != null &&
               _namingContainer._occasionalFields != null && 
               _namingContainer._occasionalFields.NamedControls != null && 
               _id != null) {
                Debug.Assert(_namingContainer._occasionalFields.NamedControls.Contains(_id)); 
            }
        }

        // Collect some statistic about the number of controls with occasional and 
        // rare fields.
        internal void GetRareFieldStatistics(ref int totalControls, 
            ref int withOccasionalFields, ref int withRareFields) { 
            totalControls++;
            if (_occasionalFields != null) { 
                withOccasionalFields++;
                if (_occasionalFields.RareFields != null)
                    withRareFields++;
 
                // No children: we're done
                if (_controls == null) 
                    return; 

                int controlCount = _controls.Count; 
                for (int i = 0; i < controlCount; i++) {
                    Control control = _controls[i];

                    control.GetRareFieldStatistics(ref totalControls, ref withOccasionalFields, 
                        ref withRareFields);
                } 
            } 
        }
#endif 

        protected void ClearChildState() {
            ClearChildControlState();
            ClearChildViewState(); 
        }
 
        protected void ClearChildControlState() { 
            //VSWhidbey 242621 to be consistent with ClearChildViewState, ignore calls before and during Init
            if (ControlState < ControlState.Initialized) { 
                return;
            }
            flags.Set(disableChildControlState);
            if (Page != null) { 
                Page.RegisterRequiresClearChildControlState(this);
            } 
        } 

 
        /// 
        ///    Deletes the view state information for all of the current control's child
        ///       controls.
        ///  
        protected void ClearChildViewState() {
            if(_occasionalFields != null) { 
                _occasionalFields.ControlsViewState = null; 
            }
        } 

        [SuppressMessage("Microsoft.Naming", "CA1706:ShortAcronymsShouldBeUppercase", MessageId="Member")]
        protected void ClearEffectiveClientIDMode() {
            EffectiveClientIDModeValue = ClientIDMode.Inherit; 
            if (HasControls()) {
                foreach (Control control in Controls) { 
                    control.ClearEffectiveClientIDMode(); 
                }
            } 
        }

        [SuppressMessage("Microsoft.Naming", "CA1706:ShortAcronymsShouldBeUppercase", MessageId="Member")]
        protected void ClearCachedClientID() { 
            _cachedPredictableID = null;
            if (HasControls()) { 
                foreach (Control control in Controls) { 
                    control.ClearCachedClientID();
                } 
            }
        }

        ///  
        ///    Indicates whether the current control's children have any saved view state
        ///       information. This property is read-only. 
        ///  
        protected bool HasChildViewState {
            get { 
                return ((_occasionalFields != null) &&
                        (_occasionalFields.ControlsViewState != null) &&
                        (_occasionalFields.ControlsViewState.Count > 0));
            } 
        }
 
 
        /// 
        /// Sets initial focus on the control 
        /// 
        public virtual void Focus() {
            Page.SetFocus(this);
        } 

        internal void LoadControlStateInternal(object savedStateObj) { 
            // Do not load the control state if it has been applied. 
            if (flags[controlStateApplied]) {
                return; 
            }

            flags.Set(controlStateApplied);
 
            Pair savedState = (Pair)savedStateObj;
            if (savedState == null) { 
                return; 
            }
            Page page = Page; 
            if (page != null && !page.ShouldLoadControlState(this)) {
                return;
            }
            // VSWhidbey160650: Only call LoadControlState with non null savedState 
            if (savedState.First != null) {
                LoadControlState(savedState.First); 
            } 
            // VSWhidbey356804: Only call LoadAdapterControlState with non null savedState
            if (AdapterInternal == null || savedState.Second == null) { 
                return;
            }
            AdapterInternal.LoadAdapterControlState(savedState.Second);
        } 

 
        ///  
        /// Load the control state, which is the essential state information needed even if view state is disabled.
        ///  
        protected internal virtual void LoadControlState(object savedState) {
        }

 
        /// 
        ///    Restores the view state information from a previous page 
        ///       request that was saved by the Control.SavedState method. 
        /// 
        protected virtual void LoadViewState(object savedState) { 
            if (savedState != null) {
                ViewState.LoadViewState(savedState);

                // Load values cached out of view state 
                object visible = ViewState["Visible"];
                if (visible != null) { 
                    if(!(bool)visible) { 
                        flags.Set(invisible);
                    } 
                    else {
                        flags.Clear(invisible);
                    }
                    flags.Set(visibleDirty); 
                }
            } 
        } 

        internal void LoadViewStateRecursive(object savedState) { 
            // nothing to do if we have no state
            if (savedState == null || flags[disableViewState])
                return;
 
            if (Page != null && Page.IsPostBack) {
                object controlState = null; 
                object adapterState = null; 
                ArrayList childState = null;
 
                Pair allSavedState = savedState as Pair;
                if (allSavedState != null) {
                    controlState = allSavedState.First;
                    childState = (ArrayList)allSavedState.Second; 
                }
                else { 
                    Debug.Assert(savedState is Triplet); 
                    Triplet t = (Triplet)savedState;
 
                    controlState = t.First;
                    adapterState = t.Second;
                    childState = (ArrayList)t.Third;
                } 

                try { 
                    if ((adapterState != null) && (AdapterInternal != null)) { 
                        AdapterInternal.LoadAdapterViewState(adapterState);
                    } 

                    if (controlState != null) {
                        LoadViewState(controlState);
                    } 

                    if (childState != null) { 
                        if (LoadViewStateByID) { 
                            LoadChildViewStateByID(childState);
                        } 
                        else {
                            LoadChildViewStateByIndex(childState);
                        }
                    } 
                }
                catch (InvalidCastException) { 
                    // catch all viewstate loading problems with casts.  They are most likely changed control trees. 
                    throw new HttpException(SR.GetString(SR.Controls_Cant_Change_Between_Posts));
                } 
                catch (IndexOutOfRangeException) {
                    // catch all viewstate loading problems with indeces.  They are most likely changed control trees.
                    throw new HttpException(SR.GetString(SR.Controls_Cant_Change_Between_Posts));
                } 
            }
 
            _controlState = ControlState.ViewStateLoaded; 
        }
 
        internal void LoadChildViewStateByID(ArrayList childState) {
            int childStateCount = childState.Count;
            for (int i = 0; i < childStateCount; i += 2) {
                // first element is index or ID of control with state and the 
                // next element is state of the control
                string controlId = (string)childState[i]; 
                object state = childState[i + 1]; 

                Control childControl = FindControl(controlId); 
                if (childControl != null) {
                    childControl.LoadViewStateRecursive(state);
                }
                else { 
                    // couldn't find a control for this state blob, save it for later
                    EnsureOccasionalFields(); 
                    if (_occasionalFields.ControlsViewState == null) { 
                        _occasionalFields.ControlsViewState = new Hashtable();
                    } 
                    _occasionalFields.ControlsViewState[controlId] = state;
                }
            }
        } 

        internal void LoadChildViewStateByIndex(ArrayList childState) { 
            ControlCollection ctrlColl = Controls; 
            int ctrlCount = ctrlColl.Count;
 
            int childStateCount = childState.Count;
            for (int i = 0; i < childStateCount; i += 2) {
                // first element is index of control with state and the
                // next element is state of the control 
                int controlIndex = (int)childState[i];
                object state = childState[i + 1]; 
 
                if (controlIndex < ctrlCount) {
                    // we have a control for this state blob 
                    ctrlColl[controlIndex].LoadViewStateRecursive(state);
                }
                else {
                    // couldn't find a control for this state blob, save it for later 
                    EnsureOccasionalFields();
                    if (_occasionalFields.ControlsViewState == null) { 
                        _occasionalFields.ControlsViewState = new Hashtable(); 
                    }
                    _occasionalFields.ControlsViewState[controlIndex] = state; 
                }
            }
        }
 
        ///
        /// Figure out if a path is physical or virtual.  This is useful because a number of our controls 
        /// accept either type of path for the same attribute. 
        ///
        internal void ResolvePhysicalOrVirtualPath(string path, out VirtualPath virtualPath, out string physicalPath) { 
            if (System.Web.Util.UrlPath.IsAbsolutePhysicalPath(path)) {
                physicalPath = path;
                virtualPath = null;
            } 
            else {
                physicalPath = null; 
 
                // It could be relative, so resolve it
                virtualPath = TemplateControlVirtualDirectory.Combine(VirtualPath.Create(path)); 
            }
        }

 
        /// 
        ///  
        ///   This function takes a virtual path, that is a relative or root relative URL without a protocol. 
        ///   It returns the mapped physcial file name relative to the template source. It throws an exception if
        ///   there is insufficient security access to read or investigate the mapped result. This should be used 
        ///   by controls that can read files and live in fully trusted DLLs such as System.Web.dll to prevent
        ///   security issues. The exception thrown does not give away information about the mapping.  For absolute
        ///   physical paths, this function checks permission
        ///  
        /// 
        protected internal string MapPathSecure(string virtualPath) { 
            if (String.IsNullOrEmpty(virtualPath)) { 
                throw new ArgumentNullException("virtualPath", SR.GetString(SR.VirtualPath_Length_Zero));
            } 

            string physicalPath;
            VirtualPath virtualPathObject;
            ResolvePhysicalOrVirtualPath(virtualPath, out virtualPathObject, out physicalPath); 
            if (physicalPath == null) {
                physicalPath = virtualPathObject.MapPathInternal(TemplateControlVirtualDirectory, 
                    true /*allowCrossAppMapping*/); 
            }
 
            // Security check
            HttpRuntime.CheckFilePermission(physicalPath);

            return physicalPath; 
        }
 
 
        /// 
        ///  
        ///   This function takes a virtual path, that is a relative or root relative URL without a protocol.
        ///   It can also take a physical path, either local (c:\) or UNC.
        ///   It returns a stream used to read to contents of the file. It throws an exception if
        ///   there is insufficient security access to read or investigate the mapped result. This should be used 
        ///   by controls that can read files and live in fully trusted DLLs such as System.Web.dll to prevent
        ///   security issues. The exception thrown does not give away information about the mapping.  For absolute 
        ///   physical paths, this function checks permission 
        /// 
        ///  
        protected internal Stream OpenFile(string path) {

            string physicalPath = null;
            VirtualFile vfile = null; 

            // Need to Trim it since MapPath no longer allows trailing space (VSWhidbey 441210) 
            path = path.Trim(); 

            if (UrlPath.IsAbsolutePhysicalPath(path)) { 
                // Absolute physical path
                physicalPath = path;
            }
            else { 
                vfile = HostingEnvironment.VirtualPathProvider.GetFile(path);
                MapPathBasedVirtualFile mapPathVFile = vfile as MapPathBasedVirtualFile; 
                if (mapPathVFile != null) { 
                    physicalPath = mapPathVFile.PhysicalPath;
                } 
            }

            // If we got a physical path, make sure the user has access to it
            if (physicalPath != null) { 
                HttpRuntime.CheckFilePermission(physicalPath);
            } 
 
            if (vfile != null) {
                return vfile.Open(); 
            }
            else {
                return new FileStream(physicalPath, FileMode.Open, FileAccess.Read, FileShare.Read);
            } 
        }
 
        /// 
        /// Open a stream from either a virtual or physical path, and if possible get a CacheDependency
        /// for the resulting Stream. 
        ///
        internal Stream OpenFileAndGetDependency(VirtualPath virtualPath, string physicalPath, out CacheDependency dependency) {

            // Only one of the paths should be non-null 
            Debug.Assert((virtualPath == null) != (physicalPath == null));
 
            // If we got a virtual path, and we're using the default VPP, call MapPath 
            if (physicalPath == null && HostingEnvironment.UsingMapPathBasedVirtualPathProvider) {
                physicalPath = virtualPath.MapPathInternal(TemplateControlVirtualDirectory, 
                    true /*allowCrossAppMapping*/);
            }

            Stream stream; 
            if (physicalPath != null) {
                // Security check 
                HttpRuntime.CheckFilePermission(physicalPath); 

                // Work directly with the physical file, bypassing the VPP 
                stream = new FileStream(physicalPath, FileMode.Open, FileAccess.Read, FileShare.Read);
                dependency = new CacheDependency(0, physicalPath);
            }
            else { 
                // It's non file system based, so go though the VirtualPathProvider
                stream = virtualPath.OpenFile(); 
                dependency = VirtualPathProvider.GetCacheDependency(virtualPath); 
            }
 
            return stream;
        }

 
        /// 
        /// Raises the  
        /// event. This notifies the control that it should perform any work that needs to 
        /// occur for each page request.
        ///  
        protected internal virtual void OnLoad(EventArgs e) {
            if(HasEvents()) {
                EventHandler handler = _events[EventLoad] as EventHandler;
                if(handler != null) { 
                    handler(this, e);
                } 
            } 
        }
 
        internal virtual void LoadRecursive() {

            // Only make the actual call if it hasn't already happened (ASURT 111303)
            if (_controlState < ControlState.Loaded) { 
                if (AdapterInternal != null) {
                    AdapterInternal.OnLoad(EventArgs.Empty); 
                } 
                else {
                    OnLoad(EventArgs.Empty); 
                }
            }

            // Call Load on all our children 
            if (_controls != null) {
                string oldmsg = _controls.SetCollectionReadOnly(SR.Parent_collections_readonly); 
 
                int controlCount = _controls.Count;
                for (int i = 0; i < controlCount; i++) { 
                    _controls[i].LoadRecursive();
                }

                _controls.SetCollectionReadOnly(oldmsg); 
            }
 
            if (_controlState < ControlState.Loaded) 
                _controlState = ControlState.Loaded;
        } 


        /// 
        /// Raises the  event. This method uses event arguments 
        ///    to pass the event data to the control.
        ///  
        protected internal virtual void OnPreRender(EventArgs e) { 
            if(HasEvents()) {
                EventHandler handler = _events[EventPreRender] as EventHandler; 
                if (handler != null) {
                    handler(this, e);
                }
            } 
        }
 
        internal virtual void PreRenderRecursiveInternal() { 
            // Call Visible property and cache value in !flags[invisible] to allow Visible to be overridden.
            // This avoids unnecessary virtual property calls in SaveViewState and Render. 
            bool visible = Visible;
            if(!visible) {
                flags.Set(invisible);
            } 
            else {
                flags.Clear(invisible); 
                EnsureChildControls(); 

                if (AdapterInternal != null) { 
                    AdapterInternal.OnPreRender(EventArgs.Empty);
                }
                else {
                    OnPreRender(EventArgs.Empty); 
                }
 
                if (_controls != null) { 
                    string oldmsg = _controls.SetCollectionReadOnly(SR.Parent_collections_readonly);
 
                    int controlCount = _controls.Count;
                    for (int i=0; i < controlCount; i++) {
                        _controls[i].PreRenderRecursiveInternal();
                    } 
                    _controls.SetCollectionReadOnly(oldmsg);
                } 
            } 
            _controlState = ControlState.PreRendered;
        } 

        internal int EstimateStateSize(object state) {
            if(state == null) {
                return 0; 
            }
            return Util.SerializeWithAssert(new ObjectStateFormatter(), state).Length; 
        } 

        /* 
         * Walk the tree and fill in profile information
         */

        ///  
        /// 
        /// Gathers information about the control and delivers it to the  
        /// property to be displayed when tracing is enabled for the page. 
        /// 
        protected void BuildProfileTree(string parentId, bool calcViewState) { 
            // estimate the viewstate size.
            calcViewState = calcViewState && (!flags[disableViewState]);
            int viewstatesize;
            if (calcViewState) 
                viewstatesize = EstimateStateSize(SaveViewState());
            else 
                viewstatesize = 0; 

            int controlstatesize = 0; 
            if(Page != null && Page._registeredControlsRequiringControlState != null && Page._registeredControlsRequiringControlState.Contains(this)) {
                controlstatesize = EstimateStateSize(SaveControlStateInternal());
            }
 
            // give it all to the profiler
            Page.Trace.AddNewControl(UniqueID, parentId, this.GetType().FullName, viewstatesize, controlstatesize); 
 
            if (_controls != null) {
                int controlCount = _controls.Count; 
                for (int i = 0; i < controlCount; i++) {
                    _controls[i].BuildProfileTree(UniqueID, calcViewState);
                }
            } 
        }
 
 
        internal object SaveControlStateInternal() {
            object controlState = SaveControlState(); 
            object adapterControlState = null;
            if (AdapterInternal != null) {
                adapterControlState = AdapterInternal.SaveAdapterControlState();
            } 
            if (controlState != null || adapterControlState != null) {
                return new Pair(controlState, adapterControlState); 
            } 
            return null;
        } 


        /// 
        /// Save the control state, which is the essential state information needed even if view state is disabled. 
        /// 
        protected internal virtual object SaveControlState() { 
            return null; 
        }
 
        // Save modified state the control would like restored on the postback.
        // Return null if there is no state to save.

        ///  
        ///    
        ///       Saves view state for use with a later  
        ///       request. 
        ///    
        ///  
        protected virtual object SaveViewState() {
            // Save values cached out of view state
            if (flags[visibleDirty]) {
                ViewState["Visible"] = !flags[invisible]; 
            }
            if (_viewState != null) 
                return _viewState.SaveViewState(); 

            return null; 
        }

        // Answer any state this control or its descendants want to save on freeze.
        // The format for saving is Triplet(myState, ArrayList childIDs, ArrayList childStates), 
        // where myState or childStates and childIDs may be null.
        internal object SaveViewStateRecursive(ViewStateMode inheritedMode) { 
            if (flags[disableViewState]) 
                return null;
 
            bool saveThisState;
            if (flags[viewStateNotInherited]) {
                if (flags[viewStateMode]) {
                    saveThisState = true; 
                    inheritedMode = ViewStateMode.Enabled;
                } 
                else { 
                    saveThisState = false;
                    inheritedMode = ViewStateMode.Disabled; 
                }
            }
            else {
                saveThisState = (inheritedMode == ViewStateMode.Enabled); 
            }
 
            object adapterState = null; 
            object controlSavedState = null;
 
            if (saveThisState) {
                if (AdapterInternal != null) {
                    adapterState = AdapterInternal.SaveAdapterViewState();
                } 
                controlSavedState = SaveViewState();
            } 
 
            ArrayList childStates = null;
            if (HasControls()) { 
                ControlCollection occasionalFieldControls = _controls;
                int occasionalFieldControlCount = occasionalFieldControls.Count;

                bool useId = LoadViewStateByID; 
                for (int i = 0; i < occasionalFieldControlCount; i++) {
                    Control child = occasionalFieldControls[i]; 
                    object childState = child.SaveViewStateRecursive(inheritedMode); 
                    if (childState != null) {
                        if (childStates == null) { 
                            childStates = new ArrayList(occasionalFieldControlCount);
                        }

                        if (useId) { 
                            child.EnsureID();
                            childStates.Add(child.ID); 
                        } 
                        else {
                            childStates.Add(i); 
                        }
                        childStates.Add(childState);
                    }
                } 
            }
 
            if (AdapterInternal != null) { 
                if ((controlSavedState != null) || (adapterState != null) || (childStates != null)) {
                    return new Triplet(controlSavedState, adapterState, childStates); 
                }
            }
            else {
                if ((controlSavedState != null) || (childStates != null)) { 
                    return new Pair(controlSavedState, childStates);
                } 
            } 

            return null; 
        }


        ///  
        /// Outputs control content to a provided HTMLTextWriter
        /// output stream. 
        ///  
        protected internal virtual void Render(HtmlTextWriter writer) {
            RenderChildren(writer); 
        }

        internal void RenderChildrenInternal(HtmlTextWriter writer, ICollection children) {
            // If we have a delegate, use it for the rendering. 
            // This happens when there is some ASP code.  See also Whidbey 33012.
            if(RareFields != null && RareFields.RenderMethod != null ) { 
                writer.BeginRender(); 
                RareFields.RenderMethod(writer, this);
                writer.EndRender(); 
                return;
            }
            if (children != null) {
                foreach (Control child in children) { 
                    child.RenderControl(writer);
                } 
            } 
        }
 
        protected internal virtual void RenderChildren(HtmlTextWriter writer) {
            ICollection children = _controls;
            RenderChildrenInternal(writer, children);
        } 

        ///  
        ///    [To be supplied.] 
        /// 
        [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")] 
        public virtual void RenderControl(HtmlTextWriter writer) {
            //use the Adapter property to ensure it is resolved
            RenderControl(writer, Adapter);
        } 

        ///  
        ///    Used for MobilePage implementation. 
        /// 
        protected void RenderControl(HtmlTextWriter writer, ControlAdapter adapter) { 
            if (!flags[invisible] && !flags[notVisibleOnPage]) {
                HttpContext context = (Page == null) ? null : Page._context;
                if (context  != null && context.TraceIsEnabled) {
                    int presize = context.Response.GetBufferedLength(); 
                    RenderControlInternal(writer, adapter);
                    int postsize = context.Response.GetBufferedLength(); 
                    context.Trace.AddControlSize(UniqueID, postsize - presize); 
                }
                else { 
                    RenderControlInternal(writer, adapter);
                }
            }
        } 

        private void RenderControlInternal(HtmlTextWriter writer, ControlAdapter adapter) { 
            if (adapter != null) { 
                //
                adapter.BeginRender(writer); 
                adapter.Render(writer);
                adapter.EndRender(writer);
            }
            else { 
                Render(writer);
            } 
        } 

 
        /// 
        ///    [To be supplied.]
        /// 
        protected internal virtual void OnUnload(EventArgs e) { 
            if(HasEvents()) {
                EventHandler handler = _events[EventUnload] as EventHandler; 
                if (handler != null) { 
                    handler(this, e);
                } 
            }
        }

 
        /// 
        ///    Enables a control to perform final cleanup. 
        ///  
        public virtual void Dispose() {
            IContainer container = null; 

            if (Site != null) {
                container = (IContainer)Site.GetService(typeof(IContainer));
                if (container != null) { 
                    container.Remove(this);
                    EventHandler disp = Events[EventDisposed] as EventHandler; 
                    if (disp != null) 
                        disp(this, EventArgs.Empty);
                } 
            }

            if (_occasionalFields != null) {
                _occasionalFields.Dispose(); 
                //do not null out for backwards compat, VSWhidbey 475940
                //_occasionalFields = null; 
            } 

            if (_events != null) { 
                _events.Dispose();
                _events = null;
            }
        } 

 
        internal virtual void UnloadRecursive(bool dispose) { 
            Page page = Page;
            if (page != null && page.RequiresControlState(this)) { 
                page.UnregisterRequiresControlState(this);
                RareFieldsEnsured.RequiredControlState = true;
            }
 
            // Remove the generated ID so it will be assigned a different ID next time.
            if (flags[useGeneratedID]) { 
                _id = null; 
                flags.Clear(useGeneratedID);
            } 

            if (_controls != null) {
                string oldmsg = _controls.SetCollectionReadOnly(SR.Parent_collections_readonly);
 
                int controlCount = _controls.Count;
                for (int i = 0; i < controlCount; i++) 
                    _controls[i].UnloadRecursive(dispose); 

                _controls.SetCollectionReadOnly(oldmsg); 
            }

            if (AdapterInternal != null) {
                AdapterInternal.OnUnload(EventArgs.Empty); 
            }
            else { 
                OnUnload(EventArgs.Empty); 
            }
 
            //
            if (dispose)
                Dispose();
 
            // VSWhidbey 244999: Everett behavior doesn't reset the control state.
            // But for control which requires its OnInit method to be called again 
            // to properly initialize when the control is removed and added back 
            // to Page's control tree, the control can override IsReloadable
            // to true so the control state is reset.  e.g. Validator, see bug 
            if (IsReloadable) {
                _controlState = ControlState.Constructed;
            }
        } 

 
        ///  
        ///    Assigns an sources of the event and its information up the page control
        ///       hierarchy until they reach the top of the control tree.  
        /// 
        protected void RaiseBubbleEvent(object source, EventArgs args) {
            Control currentTarget = Parent;
            while (currentTarget != null) { 
                if (currentTarget.OnBubbleEvent(source, args)) {
                    return; 
                } 
                currentTarget = currentTarget.Parent;
            } 
        }


        ///  
        ///    Determines whether the event for the control should be passed up the page's
        ///       control hierarchy. 
        ///  
        protected virtual bool OnBubbleEvent(object source, EventArgs args) {
            return false; 
        }


        // Members related to being a container 

 
        ///  
        ///     Gets a ControlCollection object that represents the child controls for a specified control in the
        ///       UI hierarchy. 
        /// 
        [
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), 
        WebSysDescription(SR.Control_Controls)
        ] 
        public virtual ControlCollection Controls { 
            get {
                if (_controls == null) { 
                    _controls = CreateControlCollection();
                }
                return _controls;
            } 
        }
 
 
        /// 
        ///    Indicates a dictionary of state information that allows you to save and restore 
        ///       the state of a control across multiple requests for the same page.
        /// 
        [
        Browsable(false), 
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden),
        WebSysDescription(SR.Control_State) 
        ] 
        protected virtual StateBag ViewState {
            get { 
                if (_viewState != null) {   // create a StateBag on demand; WebControl makes its case sensitive
                    return _viewState;
                }
 
                _viewState = new StateBag(ViewStateIgnoresCase);
                if (IsTrackingViewState) 
                    _viewState.TrackViewState(); 
                return _viewState;
            } 
        }

        // fast enough that we cam always use it.
 
        /// 
        /// Indicates whether the  object is case-insensitive. 
        ///  
        [
        Browsable(false), 
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)
        ]
        protected virtual bool ViewStateIgnoresCase {
            [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")] 
            get {
                return false; 
            } 
        }
 

        /// 
        /// 
        protected internal virtual void AddedControl(Control control, int index) { 
            if (control.OwnerControl != null) {
                throw new InvalidOperationException(SR.GetString(SR.Substitution_NotAllowed)); 
            } 

            if (control._parent != null) { 
                control._parent.Controls.Remove(control);
            }

            control._parent = this; 
            control._page = Page;
            control.flags.Clear(designModeChecked); 
 
            // We only add to naming container if it is available. Otherwise, it will be pushed through
            // during InitRecursive 
            Control namingContainer = flags[isNamingContainer] ? this : _namingContainer;
            if (namingContainer != null) {
                control.UpdateNamingContainer(namingContainer);
                if (control._id == null && !control.flags[idNotRequired]) { 
                    // this will also dirty the name table in the naming container
                    control.GenerateAutomaticID(); 
                } 
                else if (control._id != null || (control._controls != null)) {
                    // If the control has and ID, or has children (which *may* themselves 
                    // have ID's), we need to dirty the name table (ASURT 100557)
                    namingContainer.DirtyNameTable();
                }
            } 

            /* 
             * The following is for times when AddChild is called after CreateChildControls. This 
             * allows users to add children at any time in the creation process without having
             * to understand the underlying machinery. 
             * Note that if page is null, it means we haven't been attached to a container ourselves.
             * If this is true, when we are, our children will be recursively set up.
             */
            if (_controlState >= ControlState.ChildrenInitialized) { 

                Debug.Assert(namingContainer != null); 
                control.InitRecursive(namingContainer); 

                // VSWhidbey 396372: We need to reregister the control state if the control is reparented because the control 
                // is unregistered during unload, but its already been inited once, so it will not get its Init called again
                // which is where most controls call RegisterRequiresControlState
                if (control._controlState >= ControlState.Initialized &&
                    control.RareFields != null && 
                    control.RareFields.RequiredControlState) {
                    Page.RegisterRequiresControlState(control); 
                } 

                if (_controlState >= ControlState.ViewStateLoaded) { 
                    object viewState = null;
                    if(_occasionalFields != null && _occasionalFields.ControlsViewState != null) {
                        viewState = _occasionalFields.ControlsViewState[index];
                        // This solution takes the conservative approach that once viewstate has been 
                        // applied to a child control, it is thrown away.  This eliminates inadvertently
                        // setting viewstate on the wrong control, which can occur in scenarios where 
                        // the child control collection is being manipulated via code.  Probably need 
                        // to provide a feature where programmer can control whether to reapply viewstate
                        // or not. 
                        if (LoadViewStateByID) {
                            control.EnsureID();
                            viewState = _occasionalFields.ControlsViewState[control.ID];
                            _occasionalFields.ControlsViewState.Remove(control.ID); 
                        }
                        else { 
                            viewState = _occasionalFields.ControlsViewState[index]; 
                            _occasionalFields.ControlsViewState.Remove(index);
                        } 
                    }

                    control.LoadViewStateRecursive(viewState);
 
                    if (_controlState >= ControlState.Loaded) {
                        control.LoadRecursive(); 
 
                        if (_controlState >= ControlState.PreRendered)
                            control.PreRenderRecursiveInternal(); 
                    }
                }
            }
        } 

 
        ///  
        ///    [To be supplied.]
        ///  
        protected virtual ControlCollection CreateControlCollection() {
            return new ControlCollection(this);
        }
 

        ///  
        ///     
        ///       Notifies any controls that use composition-based implementation to create any
        ///       child controls they contain in preperation for postback or rendering. 
        ///    
        /// 
        [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
        protected internal virtual void CreateChildControls() { 
        }
 
 

        ///  
        ///    Indicates whether the control's child controls have been created.
        /// 
        protected bool ChildControlsCreated {
            get { 
                return flags[controlsCreated];
            } 
            set { 
                if (!value && flags[controlsCreated]) {
                    Controls.Clear(); 
                }
                if(value) {
                    flags.Set(controlsCreated);
                } 
                else {
                    flags.Clear(controlsCreated); 
                } 
            }
        } 


        /// 
        ///    Make a URL absolute using the AppRelativeTemplateSourceDirectory.  The returned URL is for 
        ///        client use, and will contain the session cookie if appropriate.
        ///  
        public string ResolveUrl(string relativeUrl) { 
            if (relativeUrl == null) {
                throw new ArgumentNullException("relativeUrl"); 
            }

            // check if its empty or already absolute
            if ((relativeUrl.Length == 0) || (UrlPath.IsRelativeUrl(relativeUrl) == false)) { 
                return relativeUrl;
            } 
 
            string baseUrl = AppRelativeTemplateSourceDirectory;
            if (String.IsNullOrEmpty(baseUrl)) { 
                return relativeUrl;
            }

            // first make it absolute 
            string url = UrlPath.Combine(baseUrl, relativeUrl);
 
            // include the session cookie if available (ASURT 47658) 
            // As a side effect, this will change an app relative path (~/...) to app absolute
            return Context.Response.ApplyAppPathModifier(url); 
        }


        ///  
        ///     Return a URL that is suitable for use on the client.
        ///     If the URL is absolute, return it unchanged.  If it is relative, turn it into a 
        ///     relative URL that is correct from the point of view of the current request path 
        ///     (which is what the browser uses for resolution).
        ///  
        public string ResolveClientUrl(string relativeUrl) {
            if (DesignMode && Page != null && Page.Site != null) {
                IUrlResolutionService resolutionService = (IUrlResolutionService)Page.Site.GetService(typeof(IUrlResolutionService));
                if (resolutionService != null) { 
                    return resolutionService.ResolveClientUrl(relativeUrl);
                } 
            } 

            if (relativeUrl == null) { 
                throw new ArgumentNullException("relativeUrl");
            }

            // Get the app absolute TemplateSourceDirectory (not app relative) 
            string tplSourceDir = VirtualPath.GetVirtualPathString(TemplateControlVirtualDirectory);
            if (String.IsNullOrEmpty(tplSourceDir)) 
                return relativeUrl; 

            string baseRequestDir = Context.Request.ClientBaseDir.VirtualPathString; 

            // If the path is app relative (~/...), we cannot take shortcuts, since
            // the ~ is meaningless on the client, and must be resolved
            if (!UrlPath.IsAppRelativePath(relativeUrl)) { 

                // If the template source directory is the same as the directory of the request, 
                // we don't need to do any adjustments to the input path 
                if (StringUtil.EqualsIgnoreCase(baseRequestDir, tplSourceDir))
                    return relativeUrl; 

                // check if it's empty or absolute
                if ((relativeUrl.Length == 0) || (!UrlPath.IsRelativeUrl(relativeUrl))) {
                    return relativeUrl; 
                }
            } 
 
            // first make it absolute
            string url = UrlPath.Combine(tplSourceDir, relativeUrl); 

            // Make sure the path ends with a slash before calling MakeRelative
            baseRequestDir = UrlPath.AppendSlashToPathIfNeeded(baseRequestDir);
 
            // Now, make it relative to the current request, so that the client will
            // compute the correct path 
            url = HttpUtility.UrlPathEncode(UrlPath.MakeRelative(baseRequestDir, url)); 
            Debug.Trace("ClientUrl", "*** ResolveClientUrl (" + relativeUrl + ") --> " + url + " ***");
            return url; 
        }

        internal void DirtyNameTable() {
            Debug.Assert(this is INamingContainer); 
            if(_occasionalFields != null) {
                _occasionalFields.NamedControls = null; 
            } 
        }
 
        private void EnsureNamedControlsTable() {
            Debug.Assert(this is INamingContainer);
            Debug.Assert(HasControls());
            Debug.Assert(_occasionalFields != null); 
            Debug.Assert(_occasionalFields.NamedControls == null);
 
            _occasionalFields.NamedControls = new HybridDictionary(/*initialSize*/ _occasionalFields.NamedControlsID, /*caseInsensitive*/ true); 
            FillNamedControlsTable(this, _controls);
        } 

        private void FillNamedControlsTable(Control namingContainer, ControlCollection controls) {
            Debug.Assert(namingContainer._occasionalFields != null);
            Debug.Assert(namingContainer._occasionalFields.NamedControls != null); 
            Debug.Assert((controls != null) && (controls.Count != 0));
 
            int controlCount = controls.Count; 
            for (int i=0; i < controlCount; i++) {
                Control control = controls[i]; 
                if (control._id != null) {
#if DEBUG
                    if (control._namingContainer != null) {
                        Debug.Assert(control._namingContainer == namingContainer); 
                    }
#endif // DEBUG 
                    try { 
                        namingContainer.EnsureOccasionalFields();
                        namingContainer._occasionalFields.NamedControls.Add(control._id, control); 
                    }
                    catch {
                        throw new HttpException(SR.GetString(SR.Duplicate_id_used, control._id, "FindControl"));
                    } 
                }
                if (control.HasControls() && (control.flags[isNamingContainer] == false)) { 
                    FillNamedControlsTable(namingContainer, control.Controls); 
                }
            } 
        }


        ///  
        ///    Searches the current naming container for a control with
        ///       the specified  . 
        ///  
        public virtual Control FindControl(String id) {
            return FindControl(id, 0); 
        }


        ///  
        /// 
        ///    Searches the current naming container for a control with the specified 
        ///     and an offset to aid in the 
        ///       search.
        ///  
        protected virtual Control FindControl(String id, int pathOffset) {
            string childID;

            EnsureChildControls(); 

            // If we're not the naming container, let it do the job 
            if (!(flags[isNamingContainer])) { 
                Control namingContainer = NamingContainer;
                if (namingContainer != null) { 
                    return namingContainer.FindControl(id, pathOffset);
                }
                return null;
            } 

            // No registered control, demand create the named controls table 
            //call HasControls doesn't ensures _occasionalFields != null 
            if (HasControls()) {
                EnsureOccasionalFields(); 
                if (_occasionalFields.NamedControls == null) {
                    EnsureNamedControlsTable();
                }
            } 
            if (_occasionalFields == null || _occasionalFields.NamedControls == null) {
                return null; 
            } 

            // Need to support ':' for V1 backward compatibility. 
            char[] findControlSeparators = { ID_SEPARATOR, LEGACY_ID_SEPARATOR };

            // Is it a hierarchical name?
            int newPathOffset = id.IndexOfAny(findControlSeparators, pathOffset); 

            // If not, handle it here 
            if (newPathOffset == -1) { 
                childID = id.Substring(pathOffset);
                return _occasionalFields.NamedControls[childID] as Control; 
            }

            // Get the name of the child, and try to locate it
            childID = id.Substring(pathOffset, newPathOffset - pathOffset); 
            Control child =  _occasionalFields.NamedControls[childID] as Control;
 
            // Child doesn't exist: fail 
            if (child == null)
                return null; 

            return child.FindControl(id, newPathOffset + 1);
        }
 
        /*
         * Called when the controls of a naming container are cleared. 
         */ 
        internal void ClearNamingContainer() {
            Debug.Assert(this is INamingContainer); 

            EnsureOccasionalFields();
            _occasionalFields.NamedControlsID = 0;
            DirtyNameTable(); 
        }
 
 
        /// 
        ///  
        /// 
        [SecurityPermission(SecurityAction.Demand, Unrestricted = true)]
        protected virtual IDictionary GetDesignModeState() {
            ControlRareFields rareFields = RareFieldsEnsured; 
            if (rareFields.DesignModeState == null) {
                rareFields.DesignModeState = new HybridDictionary(); 
            } 
            return rareFields.DesignModeState;
        } 


        /// 
        ///    Determines if the current control contains any child 
        ///       controls. Since this method simply deteremines if any child controls exist at
        ///       all, it can enhance performance by avoiding a call to the Count property, 
        ///       inherited from the  class, on the  
        ///       property.
        ///  
        public virtual bool HasControls() {
            return _controls != null && _controls.Count > 0;
        }
 
        /*
         * Check if a Control either has children or has a compiled render method. 
         * This is to address issues like ASURT 94127 
         */
        internal bool HasRenderingData() { 
            return HasControls() || HasRenderDelegate();
        }

        /* 
         * Check if a Control either has children or has a compiled render method.
         * This is to address issues like ASURT 94127 
         */ 
        internal bool HasRenderDelegate() {
            if(RareFields != null) { 
                return (RareFields.RenderMethod != null );
            }
            return false;
        } 

        /* 
         * Returns true if the container contains just a static string, i.e., 
         * when the Controls collection has a single LiteralControl.
         */ 

        /// 
        ///    Determines if the container holds literal content only.
        ///       When this method returns  
        ///       , the container collection only holds a single literal control. The
        ///       content is then passed to the requesting browser as HTML. 
        ///  
        protected bool IsLiteralContent() {
            return (_controls != null) && (_controls.Count == 1) && 
            ((_controls[0] is LiteralControl));
        }

 
        /// 
        ///    Determines if view state changes to the 
        ///     
        ///    are being saved. 
        ///  
        protected bool IsTrackingViewState {
            get {
                return flags[marked];
            } 
        }
 
 
        /// 
        ///    Turns on tracking of view state changes to the control 
        ///       so that they can be stored in the 
        ///       object.
        /// 
        [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")] 
        protected virtual void TrackViewState() {
            if (_viewState != null) 
                _viewState.TrackViewState(); 

            flags.Set(marked); 
        }


        ///  
        ///    Checks that the control contains child controls; if it does not, it creates
        ///       them. This includes any literal content being parsed as a  
        ///       object.  
        /// 
        protected virtual void EnsureChildControls() { 
            if (!ChildControlsCreated && !flags[creatingControls]) {
                flags.Set(creatingControls);
                try {
                    ResolveAdapter(); 
                    if (AdapterInternal != null) {
                        AdapterInternal.CreateChildControls(); 
                    } 
                    else {
                        CreateChildControls(); 
                    }

                    // Only set ChildControlsCreated = true if CreateChildControls() did not throw
                    // an exception (VSWhidbey 465798). 
                    ChildControlsCreated = true;
                } 
                finally { 
                    flags.Clear(creatingControls);
                } 
            }
        }

        ///  
        /// Used internally to store a ControlBuilder reference for the control.
        /// The builder will be used at design-time to help persist all the filtered properties 
        /// of the control. 
        /// 
        internal void SetControlBuilder(ControlBuilder controlBuilder) { 
            RareFieldsEnsured.ControlBuilder = controlBuilder;
        }

 
        /// 
        ///  
        protected internal virtual void RemovedControl(Control control) { 
            if (control.OwnerControl != null) {
                throw new InvalidOperationException(SR.GetString(SR.Substitution_NotAllowed)); 
            }

            if ((_namingContainer != null) && (control._id != null)) {
                _namingContainer.DirtyNameTable(); 
            }
 
            // Controls may need to do their own cleanup. 
            control.UnloadRecursive(false);
 
            control._parent = null;
            control._page = null;
            control._namingContainer = null;
 
            // Don't reset template source virtual directory on TemplateControl's, because
            // the path is their own, not their parent. i.e. it doesn't change no matter 
            // where in the tree they end up. 
            if (!(control is TemplateControl)) {
                if (control._occasionalFields != null) { 
                    control._occasionalFields.TemplateSourceVirtualDirectory = null;
                }
            }
 
            if (control._occasionalFields != null ) {
                control._occasionalFields.TemplateControl = null; 
            } 

            control.flags.Clear(mustRenderID); 
            control.ClearCachedUniqueIDRecursive();
        }

        internal void SetDesignMode() { 
            flags.Set(designMode);
            flags.Set(designModeChecked); 
        } 

 
        /// 
        /// 
        /// 
        protected virtual void SetDesignModeState(IDictionary data) { 
        }
 
        // Set the delegate to the render method 

        ///  
        /// 
        ///    Assigns any event handler delegates for the control to match the parameters
        ///       defined in the . 
        ///  
        [EditorBrowsable(EditorBrowsableState.Advanced)]
        public void SetRenderMethodDelegate(RenderMethod renderMethod) { 
            RareFieldsEnsured.RenderMethod = renderMethod; 

            // Make the collection readonly if there are code blocks (ASURT 78810) 
            Controls.SetCollectionReadOnly(SR.Collection_readonly_Codeblocks);
        }

 
        /// 
        ///  
        ///    Returns whether the control contains any data binding logic. This method is 
        ///       only accessed by RAD designers.
        ///  
        bool IDataBindingsAccessor.HasDataBindings {
            get {
                return ((RareFields != null) && (RareFields.DataBindings != null) && (RareFields.DataBindings.Count != 0));
            } 
        }
 
 
        /// 
        ///  
        /// Indicates a collection of all data bindings on the control. This property is
        /// read-only.
        /// 
        DataBindingCollection IDataBindingsAccessor.DataBindings { 
            get {
                ControlRareFields rareFields = RareFieldsEnsured; 
                if (rareFields.DataBindings == null) { 
                    rareFields.DataBindings = new DataBindingCollection();
                } 
                return rareFields.DataBindings;
            }
        }
 

        // IParserAccessor interface 
        // A sub-object tag was parsed by the parser; add it to this control. 

        ///  
        /// 
        /// Notifies the control that an element, XML or HTML, was parsed, and adds it to
        /// the control.
        ///  
        [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
        void IParserAccessor.AddParsedSubObject(object obj) { 
            AddParsedSubObject(obj); 
        }
 
        internal string SpacerImageUrl {
            get {
                EnsureOccasionalFields();
                if (_occasionalFields.SpacerImageUrl == null) { 
                    _occasionalFields.SpacerImageUrl = Page.ClientScript.GetWebResourceUrl(typeof(WebControl), "Spacer.gif");
                } 
                return _occasionalFields.SpacerImageUrl; 
            }
        } 

        private Control OwnerControl {
            [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
            get { 
                if (RareFields == null) {
                    return null; 
                } 

                return RareFields.OwnerControl; 
            }
            set {
                RareFieldsEnsured.OwnerControl = value;
            } 
        }
 
        internal IPostBackDataHandler PostBackDataHandler { 
            get {
                IPostBackDataHandler pbdh = AdapterInternal as IPostBackDataHandler; 
                if(pbdh != null)
                    return pbdh;
                pbdh = this as IPostBackDataHandler;
                return pbdh; 
            }
        } 
 
        internal IPostBackEventHandler PostBackEventHandler {
            get { 
                IPostBackEventHandler pbeh = AdapterInternal as IPostBackEventHandler;
                if(pbeh != null)
                    return pbeh;
                pbeh = this as IPostBackEventHandler; 
                return pbeh;
            } 
        } 

        #region IControlDesignerAccessor implementation 

        /// 
        IDictionary IControlDesignerAccessor.UserData {
            get { 
                ControlRareFields rareFields = RareFieldsEnsured;
                if (rareFields.ControlDesignerAccessorUserData == null) { 
                    rareFields.ControlDesignerAccessorUserData = new HybridDictionary(); 
                }
                return rareFields.ControlDesignerAccessorUserData; 
            }
        }

        ///  
        /// 
        ///  
        IDictionary IControlDesignerAccessor.GetDesignModeState() { 
            return GetDesignModeState();
        } 


        /// 
        ///  
        /// 
        void IControlDesignerAccessor.SetDesignModeState(IDictionary data) { 
            SetDesignModeState(data); 
        }
 
        void IControlDesignerAccessor.SetOwnerControl(Control owner) {
            if (owner == this) {
                throw new ArgumentException(SR.GetString(SR.Control_CannotOwnSelf), "owner");
            } 
            OwnerControl = owner;
            _parent = owner.Parent; 
            _page = owner.Page; 
        }
        #endregion 

        #region IControlBuilderAccessor implementation

        ///  
        /// 
        /// A reference to the ControlBuilder that was used to construct this control (if there was one) 
        ///  
        [
        Browsable(false), 
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)
        ]
        ControlBuilder IControlBuilderAccessor.ControlBuilder {
            get { 
                return RareFields != null ? RareFields.ControlBuilder : null;
            } 
        } 
        #endregion IControlBuilderAccessor implementation
 
        #region IExpressionsAccessor


        ///  
        bool IExpressionsAccessor.HasExpressions {
            get { 
                if (RareFields == null) { 
                    return false;
                } 
                ExpressionBindingCollection expressions = RareFields.ExpressionBindings;
                return ((expressions != null) && (expressions.Count > 0));
            }
        } 

 
        ///  
        ExpressionBindingCollection IExpressionsAccessor.Expressions {
            get { 
                ExpressionBindingCollection expressions = RareFieldsEnsured.ExpressionBindings;
                if (expressions == null) {
                    expressions = new ExpressionBindingCollection();
                    RareFields.ExpressionBindings = expressions; 
                }
                return expressions; 
            } 
        }
        #endregion 

        private sealed class ControlRareFields : IDisposable {

            internal ControlRareFields() { 
            }
            public ISite Site; 
            public RenderMethod RenderMethod; 
            // Reference to the ControlBuilder used to build this control
            public ControlBuilder ControlBuilder; 
            public DataBindingCollection DataBindings;
            public Control OwnerControl;
            public ExpressionBindingCollection ExpressionBindings;
            public bool RequiredControlState = false; 

            // These fields are only used in the designer so we 
            // keep them here to prevent memory bloat at runtime 
            public IDictionary ControlDesignerAccessorUserData;
            public IDictionary DesignModeState; 

            public Version RenderingCompatibility;
            public RouteCollection RouteCollection;
            public ControlAdapter Adapter; 

            public void Dispose() { 
                //do not null out for backwards compat, VSWhidbey 475940 
                //Site = null;
                //RenderMethod = null; 
                //DataBindings = null;
                //OwnerControl = null;
                //ExpressionBindings = null;
                //Adapter = null; 
                ControlBuilder = null;
                if (OwnerControl != null) 
                { 
                    OwnerControl.Dispose();
                } 
                ControlDesignerAccessorUserData = null;
                DesignModeState = null;
                RenderingCompatibility = null;
                RouteCollection = null; 
            }
        } 
 
        private sealed class OccasionalFields : IDisposable {
            internal OccasionalFields() { 
            }

            public string SkinId;
            public IDictionary ControlsViewState; 
            public int NamedControlsID;
            // Only used if we are a naming container.  It contains all the controls 
            // in the namespace. 
            public IDictionary NamedControls;
            public ControlRareFields RareFields; 
            public String UniqueIDPrefix;

            public string SpacerImageUrl;
            public TemplateControl TemplateControl; 
            public VirtualPath TemplateSourceVirtualDirectory;
 
            public void Dispose() { 
                if (RareFields != null) {
                    RareFields.Dispose(); 
                }

                ControlsViewState = null;
                //do not null out for backwards compat, VSWhidbey 475940 
                //NamedControls = null;
                //UniqueIDPrefix = null; 
                //TemplateControl = null; 
                //TemplateSourceVirtualDirectory = null;
            } 
        }
    }
}

// File provided for Reference Use Only by Microsoft Corporation (c) 2007.
//------------------------------------------------------------------------------ 
// 
//     Copyright (c) Microsoft Corporation.  All rights reserved.
// 
//----------------------------------------------------------------------------- 

namespace System.Web.UI { 
    using System.Text; 
    using System.ComponentModel;
    using System; 
    using System.Collections;
    using System.Collections.Specialized;
    using System.ComponentModel.Design;
    using System.ComponentModel.Design.Serialization; 
    using System.Diagnostics.CodeAnalysis;
    using System.Globalization; 
    using System.Reflection; 
    using System.IO;
    using HttpException = System.Web.HttpException; 
    using System.Web.Configuration;
    using System.Web.UI.Adapters;
    using System.Web.UI.HtmlControls;
    using System.Web.UI.WebControls; 
    using System.Web.Util;
    using System.Web.Hosting; 
    using System.Web.Caching; 
    using System.Web.Routing;
    using System.Security.Permissions; 

    // Delegate used for the compiled template
    public delegate void RenderMethod(HtmlTextWriter output, Control container);
 
    public delegate Control BuildMethod();
 
    // Defines the properties, methods, and events that are shared by all server 
    // controls in the Web Forms page framework.
    [ 
    Bindable(true),
    DefaultProperty("ID"),
    DesignerCategory("Code"),
    Designer("System.Web.UI.Design.ControlDesigner, " + AssemblyRef.SystemDesign), 
    DesignerSerializer("Microsoft.VisualStudio.Web.WebForms.ControlCodeDomSerializer, " + AssemblyRef.MicrosoftVisualStudioWeb,  "System.ComponentModel.Design.Serialization.CodeDomSerializer, " + AssemblyRef.SystemDesign),
    Themeable(false), 
    ToolboxItemFilter("System.Web.UI", ToolboxItemFilterType.Require), 
    ToolboxItemAttribute("System.Web.UI.Design.WebControlToolboxItem, " + AssemblyRef.SystemDesign)
    ] 
    public class Control : IComponent, IParserAccessor, IUrlResolutionService, IDataBindingsAccessor, IControlBuilderAccessor, IControlDesignerAccessor, IExpressionsAccessor {

        internal static readonly object EventDataBinding = new object();
        internal static readonly object EventInit = new object(); 
        internal static readonly object EventLoad = new object();
        internal static readonly object EventUnload = new object(); 
        internal static readonly object EventPreRender = new object(); 
        private static readonly object EventDisposed = new object();
 
        internal const bool EnableViewStateDefault = true;
        internal const char ID_SEPARATOR = '$';
        private const char ID_RENDER_SEPARATOR = '_';
        internal const char LEGACY_ID_SEPARATOR = ':'; 

        private string _id; 
        // allows us to reuse the id variable to store a calculated id w/o polluting the public getter 
        private string _cachedUniqueID;
        private string _cachedPredictableID; 
        private Control _parent;

        // fields related to being a container
        private ControlState _controlState; 
        private StateBag _viewState;
 
        private EventHandlerList _events; 
        private ControlCollection _controls;
 
        // The naming container that this control leaves in.  Note that even if
        // this ctrl is a naming container, it will not point to itself, but to
        // the naming container that contains it.
        private Control _namingContainer; 
        internal Page _page;
        private OccasionalFields _occasionalFields; 
        // The virtual directory of the Page or UserControl that hosts this control. 

        // const masks into the BitVector32 
        private const int idNotCalculated           = 0x00000001;
        private const int marked                    = 0x00000002;
        private const int disableViewState          = 0x00000004;
        private const int controlsCreated           = 0x00000008; 
        private const int invisible                 = 0x00000010;
        private const int visibleDirty              = 0x00000020; 
        private const int idNotRequired             = 0x00000040; 
        private const int isNamingContainer         = 0x00000080;
        private const int creatingControls          = 0x00000100; 
        private const int notVisibleOnPage          = 0x00000200;
        private const int themeApplied              = 0x00000400;
        private const int mustRenderID              = 0x00000800;
        private const int disableTheming            = 0x00001000; 
        private const int enableThemingSet          = 0x00002000;
        private const int styleSheetApplied         = 0x00004000; 
        private const int controlAdapterResolved    = 0x00008000; 
        private const int designMode                = 0x00010000;
        private const int designModeChecked         = 0x00020000; 
        private const int disableChildControlState  = 0x00040000;
        internal const int isWebControlDisabled     = 0x00080000;
        private const int controlStateApplied       = 0x00100000;
        private const int useGeneratedID            = 0x00200000; 
        private const int viewStateNotInherited     = 0x00800000;
        private const int viewStateMode             = 0x01000000; 
        private const int clientIDMode              = 0x06000000; 
        private const int clientIDModeOffset        = 25;
        private const int effectiveClientIDMode     = 0x18000000; 
        private const int effectiveClientIDModeOffset = 27;
        #pragma warning disable 0649
        internal SimpleBitVector32 flags;
        #pragma warning restore 0649 

        private const string automaticIDPrefix = "ctl"; 
        private const string automaticLegacyIDPrefix = "_ctl"; 
        private const int automaticIDCount = 128;
        private static readonly string[] automaticIDs = new string [automaticIDCount] { 
            "ctl00", "ctl01", "ctl02", "ctl03", "ctl04", "ctl05", "ctl06",
            "ctl07", "ctl08", "ctl09", "ctl10", "ctl11", "ctl12", "ctl13",
            "ctl14", "ctl15", "ctl16", "ctl17", "ctl18", "ctl19", "ctl20",
            "ctl21", "ctl22", "ctl23", "ctl24", "ctl25", "ctl26", "ctl27", 
            "ctl28", "ctl29", "ctl30", "ctl31", "ctl32", "ctl33", "ctl34",
            "ctl35", "ctl36", "ctl37", "ctl38", "ctl39", "ctl40", "ctl41", 
            "ctl42", "ctl43", "ctl44", "ctl45", "ctl46", "ctl47", "ctl48", 
            "ctl49", "ctl50", "ctl51", "ctl52", "ctl53", "ctl54", "ctl55",
            "ctl56", "ctl57", "ctl58", "ctl59", "ctl60", "ctl61", "ctl62", 
            "ctl63", "ctl64", "ctl65", "ctl66", "ctl67", "ctl68", "ctl69",
            "ctl70", "ctl71", "ctl72", "ctl73", "ctl74", "ctl75", "ctl76",
            "ctl77", "ctl78", "ctl79", "ctl80", "ctl81", "ctl82", "ctl83",
            "ctl84", "ctl85", "ctl86", "ctl87", "ctl88", "ctl89", "ctl90", 
            "ctl91", "ctl92", "ctl93", "ctl94", "ctl95", "ctl96", "ctl97",
            "ctl98", "ctl99", 
            "ctl100", "ctl101", "ctl102", "ctl103", "ctl104", "ctl105", "ctl106", 
            "ctl107", "ctl108", "ctl109", "ctl110", "ctl111", "ctl112", "ctl113",
            "ctl114", "ctl115", "ctl116", "ctl117", "ctl118", "ctl119", "ctl120", 
            "ctl121", "ctl122", "ctl123", "ctl124", "ctl125", "ctl126", "ctl127"

        };
 
        /// 
        /// Initializes a new instance of the  class. 
        ///  
        [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
        public Control() { 
            if (this is INamingContainer)
                flags.Set(isNamingContainer);
        }
 
        private ClientIDMode ClientIDModeValue {
            get { 
                return (ClientIDMode)flags[clientIDMode, clientIDModeOffset]; 
            }
            set { 
                flags[clientIDMode, clientIDModeOffset] = (int)value;
            }
        }
 
        [SuppressMessage("Microsoft.Naming", "CA1706:ShortAcronymsShouldBeUppercase", MessageId="Member")]
        [ 
        DefaultValue(ClientIDMode.Inherit), 
        Themeable(false),
        WebCategory("Behavior"), 
        WebSysDescription(SR.Control_ClientIDMode)
        ]
        public virtual ClientIDMode ClientIDMode {
            [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")] 
            get {
                return ClientIDModeValue; 
            } 
            set {
                if (ClientIDModeValue != value) { 
                    if (value != EffectiveClientIDModeValue) {
                        ClearEffectiveClientIDMode();
                        ClearCachedClientID();
                    } 
                    ClientIDModeValue = value;
                } 
            } 
        }
 
        private ClientIDMode EffectiveClientIDModeValue {
            get {
                return (ClientIDMode)flags[effectiveClientIDMode, effectiveClientIDModeOffset];
            } 
            set {
                flags[effectiveClientIDMode, effectiveClientIDModeOffset] = (int)value; 
            } 
        }
 
        internal virtual ClientIDMode EffectiveClientIDMode {
            get {
                if (EffectiveClientIDModeValue == ClientIDMode.Inherit) {
                    EffectiveClientIDModeValue = ClientIDMode; 
                    if (EffectiveClientIDModeValue == ClientIDMode.Inherit) {
                        if (NamingContainer != null) { 
                            EffectiveClientIDModeValue = NamingContainer.EffectiveClientIDMode; 
                        }
                        else { 
                            HttpContext context = Context;
                            if (context != null) {
                                EffectiveClientIDModeValue = RuntimeConfig.GetConfig(context).Pages.ClientIDMode;
                            } 
                            else {
                                EffectiveClientIDModeValue = RuntimeConfig.GetConfig().Pages.ClientIDMode; 
                            } 
                        }
                    } 
                }
                return EffectiveClientIDModeValue;
            }
        } 

        internal string UniqueClientID { 
            get { 
                string uniqueID = UniqueID;
                if(uniqueID != null && uniqueID.IndexOf(IdSeparator) >= 0) { 
                    return uniqueID.Replace(IdSeparator, ID_RENDER_SEPARATOR);
                }
                return uniqueID;
            } 
        }
 
        internal string StaticClientID { 
            get {
                return flags[useGeneratedID] ? String.Empty : ID ?? String.Empty; 
            }
        }

        internal ControlAdapter AdapterInternal { 
            get {
                if (_occasionalFields == null || 
                    _occasionalFields.RareFields == null || 
                    _occasionalFields.RareFields.Adapter == null) {
                        return null; 
                }
                return _occasionalFields.RareFields.Adapter;
            }
            set { 
                if (value != null) {
                    RareFieldsEnsured.Adapter = value; 
                } 
                else {
                    if (_occasionalFields != null && 
                        _occasionalFields.RareFields != null &&
                        _occasionalFields.RareFields.Adapter != null) {
                            _occasionalFields.RareFields.Adapter = null;
                    } 
                }
            } 
        } 

        private string GetClientID() { 
            switch (EffectiveClientIDMode) {
                case ClientIDMode.Predictable:
                    return PredictableClientID;
                case ClientIDMode.Static: 
                    return StaticClientID;
                default: 
                    return UniqueClientID; 
            }
        } 

        private string GetPredictableClientIDPrefix() {
            string predictableIDPrefix;
 
            Control namingContainer = NamingContainer;
            if (namingContainer != null) { 
                if (_id == null) { 
                    GenerateAutomaticID();
                } 
                if (namingContainer is Page || namingContainer is MasterPage) {
                    predictableIDPrefix = _id;
                }
                else { 
                    predictableIDPrefix = namingContainer.GetClientID();
                    if (String.IsNullOrEmpty(predictableIDPrefix)) { 
                        predictableIDPrefix = _id; 
                    }
                    else { 
                        if (!String.IsNullOrEmpty(_id) && (!(this is IDataItemContainer) || (this is IDataBoundItemControl))) {
                            predictableIDPrefix = predictableIDPrefix + ID_RENDER_SEPARATOR + _id;
                        }
                    } 
                }
            } 
            else { 
                predictableIDPrefix = _id;
            } 
            return predictableIDPrefix;
        }

        private string GetPredictableClientIDSuffix() { 
            string predictableIDSuffix = null;
 
            Control dataItemContainer = DataItemContainer; 
            if (dataItemContainer != null &&
                !(dataItemContainer is IDataBoundItemControl) && 
                (!(this is IDataItemContainer) || (this is IDataBoundItemControl))) {
                Control dataKeysContainer = dataItemContainer.DataKeysContainer;
                if (dataKeysContainer != null && (((IDataKeysControl)dataKeysContainer).ClientIDRowSuffix != null) && (((IDataKeysControl)dataKeysContainer).ClientIDRowSuffix.Length > 0)) {
                    predictableIDSuffix = String.Empty; 
                    IOrderedDictionary dataKey = ((IDataKeysControl)dataKeysContainer).ClientIDRowSuffixDataKeys[((IDataItemContainer)dataItemContainer).DisplayIndex].Values;
                    foreach (string suffixName in ((IDataKeysControl)dataKeysContainer).ClientIDRowSuffix) { 
                        predictableIDSuffix = predictableIDSuffix + ID_RENDER_SEPARATOR + dataKey[suffixName].ToString(); 
                    }
                } 
                else {
                    int index = ((IDataItemContainer)dataItemContainer).DisplayIndex;
                    if (index >= 0) {
                        predictableIDSuffix = ID_RENDER_SEPARATOR + index.ToString(CultureInfo.InvariantCulture); 
                    }
                } 
            } 
            return predictableIDSuffix;
        } 

        internal string PredictableClientID {
            get {
                if (_cachedPredictableID != null) { 
                    return _cachedPredictableID;
                } 
 
                _cachedPredictableID = GetPredictableClientIDPrefix();
                string suffixID = GetPredictableClientIDSuffix(); 

                // Concatenates Predictable clientID and ClientIDRowSuffix if available
                if (!String.IsNullOrEmpty(suffixID)) {
                    if (!String.IsNullOrEmpty(_cachedPredictableID)) { 
                        _cachedPredictableID = _cachedPredictableID + suffixID;
                    } 
                    else { 
                        _cachedPredictableID = suffixID.Substring(1);
                    } 
                }
                return String.IsNullOrEmpty(_cachedPredictableID) ? String.Empty : _cachedPredictableID;
            }
        } 

        ///  
        ///    Indicates the control identifier generated by the ASP.NET framework.  
        /// 
        [ 
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden),
        WebSysDescription(SR.Control_ClientID)
        ] 
        public virtual string ClientID {
            // This property is required to render a unique client-friendly id. 
            get { 
                if (EffectiveClientIDMode != ClientIDMode.Static) {
                    // Ensure that ID is set. The assumption being made is that the caller 
                    // is likely to use the client ID in script, and to support that the
                    // control should render out an ID attribute
                    EnsureID();
                } 
                return GetClientID();
            } 
        } 

        protected char ClientIDSeparator { 
            get {
                return ID_RENDER_SEPARATOR;
            }
        } 

        ///  
        ///    [To be supplied.] 
        /// 
        [ 
        WebSysDescription(SR.Control_OnDisposed)
        ]
        public event EventHandler Disposed {
            add { 
                Events.AddHandler(EventDisposed, value);
            } 
            remove { 
                Events.RemoveHandler(EventDisposed, value);
            } 
        }

        /// 
        /// Gets the  object of the current Web request. If 
        ///    the control's context is , this will be the context of the
        ///    control's parent, unless the parent control's context is . 
        ///    If this is the case, this will be equal to the HttpContext property. 
        /// 
        [ 
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)
        ]
        protected internal virtual HttpContext Context { 
            //  Request context containing the intrinsics
            [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")] 
            get { 
                Page page = Page;
                if(page != null) { 
                    return page.Context;
                }
                return HttpContext.Current;
            } 
        }
 
        protected virtual ControlAdapter ResolveAdapter() { 
            if(flags[controlAdapterResolved]) {
                return AdapterInternal; 
            }
            if (DesignMode) {
                flags.Set(controlAdapterResolved);
                return null; 
            }
 
            HttpContext context = Context; 
            if (context != null && context.Request.Browser != null) {
                AdapterInternal = context.Request.Browser.GetAdapter(this); 
            }
            flags.Set(controlAdapterResolved);
            return AdapterInternal;
        } 

        ///  
        ///    Indicates the list of event handler delegates for the control. This property 
        ///       is read-only.
        ///  
        protected ControlAdapter Adapter {
            get {
                if(flags[controlAdapterResolved]) {
                    return AdapterInternal; 
                }
                AdapterInternal = ResolveAdapter(); 
                flags.Set(controlAdapterResolved); 
                return AdapterInternal;
            } 
        }

        /// 
        /// Indicates whether a control is being used in the context of a design surface. 
        /// 
        protected internal bool DesignMode { 
            get { 
                if(!flags[designModeChecked]) {
                    Page page = Page; 
                    if(page != null )  {
                        if(page.GetDesignModeInternal()) {
                            flags.Set(designMode);
                        } 
                        else {
                            flags.Clear(designMode); 
                        } 
                    }
                    else { 
                        if(Site != null) {
                            if(Site.DesignMode) {
                                flags.Set(designMode);
                            } 
                            else {
                                flags.Clear(designMode); 
                            } 
                        }
                        else if (Parent != null) { 
                            if(Parent.DesignMode) {
                                flags.Set(designMode);
                            }
 
                            // VSWhidbey 535747: If Page, Site and Parent are all null, do not change the
                            // designMode flag since it might had been previously set by the controlBuilder. 
                            // This does not affect runtime since designMode is by-default false. 
                            /*
                            else { 
                                flags.Clear(designMode);
                            }
                            */
                        } 
                    }
                    flags.Set(designModeChecked); 
                } 
                return flags[designMode];
 
            }
        }

        // Helper function to call validateEvent. 
        internal void ValidateEvent(string uniqueID) {
            ValidateEvent(uniqueID, String.Empty); 
        } 

        // Helper function to call validateEvent. 
        internal void ValidateEvent(string uniqueID, string eventArgument) {
            if (Page != null && SupportsEventValidation) {
                Page.ClientScript.ValidateEvent(uniqueID, eventArgument);
            } 
        }
 
        // Indicates whether the control supports event validation 
        // By default, all web controls in System.Web assembly supports it but not custom controls.
        private bool SupportsEventValidation { 
            get {
                return SupportsEventValidationAttribute.SupportsEventValidation(this.GetType());
            }
        } 

        ///  
        ///    Indicates the list of event handler delegates for the control. This property 
        ///       is read-only.
        ///  
        protected EventHandlerList Events {
            [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
            get {
                if (_events == null) { 
                    _events = new EventHandlerList();
                } 
                return _events; 
            }
        } 

        [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
        protected bool HasEvents() {
            return (_events != null); 
        }
 
        ///  
        ///     Gets or sets the identifier for the control. Setting the
        ///       property on a control allows programmatic access to the control's properties. If 
        ///       this property is not specified on a control, either declaratively or
        ///       programmatically, then you cannot write event handlers and the like for the control.
        /// 
        [ 
        ParenthesizePropertyName(true),
        MergableProperty(false), 
        Filterable(false), 
        Themeable(false),
        WebSysDescription(SR.Control_ID) 
        ]
        public virtual string ID {
            get {
                if (!flags[idNotCalculated] && !flags[mustRenderID]) { 
                    return null;
                } 
                return _id; 
            }
            set { 
                // allow the id to be unset
                if (value != null && value.Length == 0)
                    value = null;
 
                string oldID = _id;
 
                _id = value; 
                ClearCachedUniqueIDRecursive();
                flags.Set(idNotCalculated); 
                flags.Clear(useGeneratedID);

                // Update the ID in the naming container
                if ((_namingContainer != null) && (oldID != null)) { 
                    _namingContainer.DirtyNameTable();
                } 
 
                if (oldID != null && oldID != _id) {
                    ClearCachedClientID(); 
                }
            }
        }
 

        ///  
        ///    Gets and sets a value indicating whether theme is enabled. 
        /// 
        [ 
        Browsable(false),
        DefaultValue(true),
        Themeable(false),
        WebCategory("Behavior"), 
        WebSysDescription(SR.Control_EnableTheming)
        ] 
        public virtual bool EnableTheming { 
            get {
                if (flags[enableThemingSet]) { 
                    return !flags[disableTheming];
                }

                if (Parent != null) { 
                    return Parent.EnableTheming;
                } 
 
                return !flags[disableTheming];
            } 
            set {
                if ((_controlState >= ControlState.FrameworkInitialized) && !DesignMode) {
                    throw new InvalidOperationException(SR.GetString(SR.PropertySetBeforePreInitOrAddToControls, "EnableTheming"));
                } 

                if(!value) { 
                    flags.Set(disableTheming); 
                }
                else { 
                    flags.Clear(disableTheming);
                }

                flags.Set(enableThemingSet); 
            }
        } 
 
        // Serialzie the value if it's set explicitely.
        internal bool ShouldSerializeEnableTheming() { 
            return flags[enableThemingSet];;
        }

        internal bool IsBindingContainer { 
            get {
                return this is INamingContainer && !(this is INonBindingContainer); 
            } 
        }
 
        protected internal bool IsChildControlStateCleared {
            get {
                return flags[disableChildControlState];
            } 
        }
 
 
        /// 
        ///    Gets and sets the skinID of the control. 
        /// 
        [
        Browsable(false),
        DefaultValue(""), 
        Filterable(false),
        WebCategory("Behavior"), 
        WebSysDescription(SR.Control_SkinId), 
        ]
        public virtual string SkinID { 
            get {
                if(_occasionalFields != null) {
                    return _occasionalFields.SkinId == null ? String.Empty : _occasionalFields.SkinId;
                } 
                return String.Empty;
            } 
            set { 
                if (!DesignMode) {
                    if (flags[styleSheetApplied]) { 
                        throw new InvalidOperationException(SR.GetString(SR.PropertySetBeforeStyleSheetApplied, "SkinId"));
                    }

                    if (_controlState >= ControlState.FrameworkInitialized) { 
                        throw new InvalidOperationException(SR.GetString(SR.PropertySetBeforePreInitOrAddToControls, "SkinId"));
                    } 
                } 

                EnsureOccasionalFields(); 
                _occasionalFields.SkinId = value;
            }
        }
 
        private ControlRareFields RareFieldsEnsured {
            get { 
                EnsureOccasionalFields(); 
                ControlRareFields rareFields = _occasionalFields.RareFields;
                if(rareFields == null) { 
                    rareFields = new ControlRareFields();
                    _occasionalFields.RareFields = rareFields;
                }
 
                return rareFields;
            } 
        } 

        private ControlRareFields RareFields { 
            get {
                if(_occasionalFields != null) {
                    return _occasionalFields.RareFields;
                } 
                return null;
            } 
        } 

        private void EnsureOccasionalFields() { 
            if(_occasionalFields == null) {
                _occasionalFields = new OccasionalFields();
            }
        } 

 
        ///  
        ///    
        ///       Gets or sets a value indicating whether the control should maintain its view 
        ///       state, and the view state of any child control in contains, when the current
        ///       page request ends.
        ///    
        ///  
        [
        DefaultValue(EnableViewStateDefault), 
        Themeable(false), 
        WebCategory("Behavior"),
        WebSysDescription(SR.Control_MaintainState) 
        ]
        public virtual bool EnableViewState {
            get {
                return !flags[disableViewState]; 
            }
            set { 
                SetEnableViewStateInternal(value); 
            }
        } 

        [
        DefaultValue(ViewStateMode.Inherit),
        Themeable(false), 
        WebCategory("Behavior"),
        WebSysDescription(SR.Control_ViewStateMode) 
        ] 
        public virtual ViewStateMode ViewStateMode {
            get { 
                return flags[viewStateNotInherited] ?
                    (flags[viewStateMode] ? ViewStateMode.Enabled : ViewStateMode.Disabled) :
                    ViewStateMode.Inherit;
            } 
            set {
                if ((value < ViewStateMode.Inherit) || (value > ViewStateMode.Disabled)) { 
                    throw new ArgumentOutOfRangeException("value"); 
                }
                if (value == ViewStateMode.Inherit) { 
                    flags.Clear(viewStateNotInherited);
                }
                else {
                    flags.Set(viewStateNotInherited); 
                    if (value == ViewStateMode.Enabled) {
                        flags.Set(viewStateMode); 
                    } 
                    else {
                        flags.Clear(viewStateMode); 
                    }
                }
            }
        } 

 
        internal void SetEnableViewStateInternal(bool value) { 
            if (!value)
                flags.Set(disableViewState); 
            else
                flags.Clear(disableViewState);
        }
 

        ///  
        /// Gets a value indicating whether the control is maintaining its view 
        /// state, when the current page request ends by looking at its own EnableViewState
        /// value, and the value for all its parents. 
        /// 
        protected internal bool IsViewStateEnabled {
            get {
                Control current = this; 
                while (current != null) {
                    if (current.EnableViewState == false) { 
                        return false; 
                    }
                    ViewStateMode mode = current.ViewStateMode; 
                    if (mode != ViewStateMode.Inherit) {
                        return (mode == ViewStateMode.Enabled);
                    }
                    current = current.Parent; 
                }
                return true; 
            } 
        }
 

        /// 
        ///    Gets the reference to the current control's naming container.
        ///  
        [
        Bindable(false), 
        Browsable(false), 
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden),
        WebSysDescription(SR.Control_NamingContainer) 
        ]
        public virtual Control NamingContainer {
            get {
                if (_namingContainer == null) { 
                    if (Parent != null) {
                        // Search for the closest naming container in the tree 
                        if (Parent.flags[isNamingContainer]) 
                            _namingContainer = Parent;
                        else 
                            _namingContainer = Parent.NamingContainer;
                    }
                }
 
                return _namingContainer;
            } 
        } 

        ///  
        /// 
        ///    Returns the databinding container of this control.  In most cases,
        ///     this is the same as the NamingContainer. But when using LoadTemplate(),
        ///     we get into a situation where that is not the case (ASURT 94138) 
        ///     The behavior is different than V1 that Usercontrol.BindingContainer is no
        ///     longer the UserControl but the control contains it. The behavior is consistent 
        ///     with LoadTemplate() case. 
        /// 
        [ 
        Bindable(false),
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden),
        EditorBrowsable(EditorBrowsableState.Never) 
        ]
        public Control BindingContainer { 
            get { 
                Control bindingContainer = NamingContainer;
                while (bindingContainer is INonBindingContainer) { 
                    bindingContainer = bindingContainer.BindingContainer;
                }

                return bindingContainer; 
            }
        } 
 
        [
        Bindable(false), 
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden),
        EditorBrowsable(EditorBrowsableState.Never)
        ] 
        public Control DataItemContainer {
            get { 
                Control dataItemContainer = NamingContainer; 
                while (dataItemContainer != null && !(dataItemContainer is IDataItemContainer)) {
                    dataItemContainer = dataItemContainer.DataItemContainer; 
                }

                return dataItemContainer;
            } 
        }
 
        [ 
        Bindable(false),
        Browsable(false), 
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden),
        EditorBrowsable(EditorBrowsableState.Never)
        ]
        public Control DataKeysContainer { 
            get {
                Control dataKeysContainer = NamingContainer; 
                while (dataKeysContainer != null && !(dataKeysContainer is IDataKeysControl)) { 
                    dataKeysContainer = dataKeysContainer.DataKeysContainer;
                } 

                return dataKeysContainer;
            }
        } 

 
 
        /// 
        ///  
        /// VSWhidbey 80467: Need to adapt id separator.
        /// 
        protected char IdSeparator {
            [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")] 
            get {
                if (Page != null) { 
                    return Page.IdSeparator; 
                }
                return IdSeparatorFromConfig; 
            }
        }

        // VSWhidbey 475945: Use the old id separator if configured 
        internal char IdSeparatorFromConfig {
            get { 
                return ((EnableLegacyRendering) ? LEGACY_ID_SEPARATOR : ID_SEPARATOR); 
            }
        } 

        // VSWhidbey 244374: Allow controls to opt into loading view state by ID instead of index (perf hit)
        protected bool LoadViewStateByID {
            get { 
                return ViewStateModeByIdAttribute.IsEnabled(GetType());
            } 
        } 

        ///  
        ///  Gets the  object that contains the
        ///    current control.
        /// 
        [ 
        Bindable(false),
        Browsable(false), 
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), 
        WebSysDescription(SR.Control_Page)
        ] 
        public virtual Page Page {
            get {
                if (_page == null) {
                    if (Parent != null) { 
                        _page = Parent.Page;
                    } 
                } 
                return _page;
            } 

            set {
                if (OwnerControl != null) {
                    throw new InvalidOperationException(); 
                }
                // This is necessary because we need to set the page in generated 
                // code before controls are added to the tree (ASURT 75330) 
                Debug.Assert(_page == null);
                Debug.Assert(Parent == null || Parent.Page == null); 
                _page = value;
            }
        }
 
        internal RouteCollection RouteCollection {
            get { 
                if (_occasionalFields == null || 
                    _occasionalFields.RareFields == null ||
                    _occasionalFields.RareFields.RouteCollection == null) { 
                        return RouteTable.Routes;
                }
                return _occasionalFields.RareFields.RouteCollection;
            } 
            set {
                if (value != null) { 
                    RareFieldsEnsured.RouteCollection = value; 
                }
                else { 
                    if (_occasionalFields != null &&
                        _occasionalFields.RareFields != null &&
                        _occasionalFields.RareFields.RouteCollection != null) {
                            _occasionalFields.RareFields.RouteCollection = null; 
                    }
                } 
            } 
        }
 
        // VSWhidbey 244999
        internal virtual bool IsReloadable {
            [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
            get { 
                return false;
            } 
        } 

        // DevDiv 33149, 43258: A backward compat. switch for Everett rendering 
        internal bool EnableLegacyRendering {
            get {
                Page page = Page;
                if (page != null) { 
                    return (page.XhtmlConformanceMode == XhtmlConformanceMode.Legacy);
                } 
                else if (DesignMode || Adapter != null) { 
                    return false;
                } 
                else {
                    return (GetXhtmlConformanceSection().Mode == XhtmlConformanceMode.Legacy);
                }
            } 
        }
 
        internal XhtmlConformanceSection GetXhtmlConformanceSection() { 
            HttpContext context = Context;
            XhtmlConformanceSection xhtmlConformanceSection; 
            if (context != null) {
                // if context is available, use the most efficient way to get the section
                xhtmlConformanceSection = RuntimeConfig.GetConfig(context).XhtmlConformance;
            } 
            else {
                xhtmlConformanceSection = RuntimeConfig.GetConfig().XhtmlConformance; 
            } 
            Debug.Assert(xhtmlConformanceSection != null);
            return xhtmlConformanceSection; 
        }

        [
        Bindable(false), 
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), 
        ] 
        public virtual Version RenderingCompatibility {
            get { 
                if (_occasionalFields == null ||
                    _occasionalFields.RareFields == null ||
                    _occasionalFields.RareFields.RenderingCompatibility == null) {
                        return RuntimeConfig.Pages.ControlRenderingCompatibilityVersion; 
                }
                return _occasionalFields.RareFields.RenderingCompatibility; 
            } 
            set {
                if (value != null) { 
                    RareFieldsEnsured.RenderingCompatibility = value;
                }
                else {
                    if (_occasionalFields != null && 
                        _occasionalFields.RareFields != null &&
                        _occasionalFields.RareFields.RenderingCompatibility != null) { 
                            _occasionalFields.RareFields.RenderingCompatibility = null; 
                    }
                } 
            }
        }

        private RuntimeConfig RuntimeConfig { 
            get {
                HttpContext context = Context; 
                if (context != null) { 
                    // if context is available, use the most efficient way to get the config
                    return RuntimeConfig.GetConfig(context); 
                } else {
                    return RuntimeConfig.GetConfig();
                }
            } 
        }
 
        [SuppressMessage("Microsoft.Design", "CA1055:UriReturnValuesShouldNotBeStrings", 
            Justification = "Consistent with other URL properties in ASP.NET.")]
        public string GetRouteUrl(object routeParameters) { 
            return GetRouteUrl(new RouteValueDictionary(routeParameters));
        }

        [SuppressMessage("Microsoft.Design", "CA1055:UriReturnValuesShouldNotBeStrings", 
            Justification = "Consistent with other URL properties in ASP.NET.")]
        public string GetRouteUrl(string routeName, object routeParameters) { 
            return GetRouteUrl(routeName, new RouteValueDictionary(routeParameters)); 
        }
 
        [SuppressMessage("Microsoft.Design", "CA1055:UriReturnValuesShouldNotBeStrings",
            Justification = "Consistent with other URL properties in ASP.NET.")]
        public string GetRouteUrl(RouteValueDictionary routeParameters) {
            return GetRouteUrl(null, routeParameters); 
        }
 
        [SuppressMessage("Microsoft.Design", "CA1055:UriReturnValuesShouldNotBeStrings", 
            Justification = "Consistent with other URL properties in ASP.NET.")]
        public string GetRouteUrl(string routeName, RouteValueDictionary routeParameters) { 
            VirtualPathData data = RouteCollection.GetVirtualPath(Context.Request.RequestContext, routeName, routeParameters);
            if (data != null) {
                return data.VirtualPath;
            } 
            return null;
        } 
 
        /// 
        ///    Gets the reference to the  
        ///    that hosts the control.
        /// 
        internal virtual TemplateControl GetTemplateControl() {
            if (_occasionalFields == null || _occasionalFields.TemplateControl == null) { 
                if (Parent != null) {
                    TemplateControl templateControl = Parent.GetTemplateControl(); 
                    if (templateControl != null) { 
                        EnsureOccasionalFields();
                        _occasionalFields.TemplateControl = templateControl; 
                    }
                }
            }
            return (_occasionalFields != null) ? _occasionalFields.TemplateControl : null; 
        }
 
 
        /// 
        ///    Gets the reference to the  
        ///    that hosts the control.
        /// 
        [
        Bindable(false), 
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), 
        WebSysDescription(SR.Control_TemplateControl) 
        ]
        public TemplateControl TemplateControl { 
            get {
                return GetTemplateControl();
            }
 
            [EditorBrowsable(EditorBrowsableState.Never)]
            set { 
                // This setter is necessary so that controls inside templates are based on 
                // hosting pages not where the templates are used.
                if (value != null) { 
                    EnsureOccasionalFields();
                    _occasionalFields.TemplateControl = value;
                }
                else { 
                    if (_occasionalFields != null &&
                        _occasionalFields.TemplateControl != null) { 
                            _occasionalFields.TemplateControl = null; 
                    }
                } 
            }
        }

        /* 
         * Determine whether this control is a descendent of the passed in control
         */ 
        internal bool IsDescendentOf(Control ancestor) { 
            Control current = this;
            while (current != ancestor && current.Parent != null) { 
                current = current.Parent;
            }
            return (current == ancestor);
        } 

 
        ///  
        ///     Gets the current control's parent control in the UI hierarchy.
        ///  
        [
        Bindable(false),
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), 
        WebSysDescription(SR.Control_Parent)
        ] 
        public virtual Control Parent { 
            [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
            get { 
                return _parent;
            }
        }
 
        internal bool IsParentedToUpdatePanel {
            get { 
                Control parent = Parent; 
                while (parent != null) {
                    if (parent is IUpdatePanel) { 
                        return true;
                    }
                    parent = parent.Parent;
                } 
                return false;
            } 
        } 

        ///  
        ///     Gets the virtual directory of the Page or UserControl that contains this control.
        /// 
        [
        Browsable(false), 
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden),
        WebSysDescription(SR.Control_TemplateSourceDirectory) 
        ] 
        public virtual string TemplateSourceDirectory {
            get { 
                if (TemplateControlVirtualDirectory == null)
                    return String.Empty;

                return TemplateControlVirtualDirectory.VirtualPathStringNoTrailingSlash; 
            }
        } 
 

        ///  
        ///     Gets the virtual directory of the Page or UserControl that contains this control.
        ///         Unlike TemplateSourceDirectory, this returns an app relative path (e.g. "~/sub")
        /// 
        [ 
        Browsable(false),
        EditorBrowsable(EditorBrowsableState.Advanced), 
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), 
        WebSysDescription(SR.Control_TemplateSourceDirectory)
        ] 
        public string AppRelativeTemplateSourceDirectory {
            get {
                return VirtualPath.GetAppRelativeVirtualPathStringOrEmpty(TemplateControlVirtualDirectory);
            } 

            [EditorBrowsable(EditorBrowsableState.Never)] 
            set { 
                // This setter is necessary so that skins are based on hosting skin file.
                this.TemplateControlVirtualDirectory = VirtualPath.CreateNonRelativeAllowNull(value); 
            }
        }

        internal VirtualPath TemplateControlVirtualDirectory { 
            get {
                if (_occasionalFields != null && _occasionalFields.TemplateSourceVirtualDirectory != null) 
                    return _occasionalFields.TemplateSourceVirtualDirectory; 

                TemplateControl control = TemplateControl; 
                if (control == null) {
                    HttpContext context = Context;
                    if (context != null) {
                        VirtualPath templateSourceVirtualDirectory = context.Request.CurrentExecutionFilePathObject.Parent; 
                        if (templateSourceVirtualDirectory != null) {
                            EnsureOccasionalFields(); 
                            _occasionalFields.TemplateSourceVirtualDirectory = templateSourceVirtualDirectory; 
                        }
                    } 
                    return (_occasionalFields != null) ? _occasionalFields.TemplateSourceVirtualDirectory : null;
                }
                // Prevent recursion if this is the TemplateControl
                if (control != this) { 
                    VirtualPath templateSourceVirtualDirectory = control.TemplateControlVirtualDirectory;
                    if (templateSourceVirtualDirectory != null) { 
                        EnsureOccasionalFields(); 
                        _occasionalFields.TemplateSourceVirtualDirectory = templateSourceVirtualDirectory;
                    } 
                }
                return (_occasionalFields != null) ? _occasionalFields.TemplateSourceVirtualDirectory : null;
            }
 
            set {
                // This setter is necessary so that skins are based on hosting skin file. 
                if (value != null) { 
                    EnsureOccasionalFields();
                    _occasionalFields.TemplateSourceVirtualDirectory = value; 
                }
                else {
                    if (_occasionalFields != null &&
                        _occasionalFields.TemplateSourceVirtualDirectory != null) { 
                            _occasionalFields.TemplateSourceVirtualDirectory = null;
                    } 
                } 
            }
        } 

        internal ControlState ControlState {
            get { return _controlState; }
            set { _controlState = value; } 
        }
 
 
        /// 
        ///    Indicates the site information for the control. 
        /// 
        [
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), 
        EditorBrowsable(EditorBrowsableState.Advanced),
        WebSysDescription(SR.Control_Site) 
        ] 
        public ISite Site {
            get { 
                if (OwnerControl != null) {
                    return OwnerControl.Site;
                }
 
                if (RareFields != null) {
                    return RareFields.Site; 
                } 
                return null;
            } 
            set {
                if (OwnerControl != null) {
                    throw new InvalidOperationException(SR.GetString(SR.Substitution_SiteNotAllowed));
                } 

                RareFieldsEnsured.Site = value; 
                flags.Clear(designModeChecked); 
            }
        } 


        /// 
        ///     
        ///       Gets or sets a value that indicates whether a control should be rendered on
        ///       the page. 
        ///     
        /// 
        [ 
        Bindable(true),
        DefaultValue(true),
        WebCategory("Behavior"),
        WebSysDescription(SR.Control_Visible) 
        ]
        public virtual bool Visible { 
            get { 
                if (flags[invisible])
                    return false; 
                else if ((_parent != null) && !DesignMode)
                    return _parent.Visible;
                else
                    return true; 
            }
            set { 
                if (flags[marked]) { 
                    bool visible = !flags[invisible];
                    if (visible != value) { 
                        flags.Set(visibleDirty);
                    }
                }
 
                if(!value) {
                    flags.Set(invisible); 
                } 
                else {
                    flags.Clear(invisible); 
                }
            }
        }
 

        ///  
        /// Do not remove or change the signature. It is called via reflection. 
        /// This allows for correct serialization, since Visible is implemented as a
        /// recursive property. 
        /// 
        private void ResetVisible() {
            Visible = true;
        } 

 
        ///  
        /// Do not remove or change the signature. It is called via reflection.
        /// This allows for correct serialization, since Visible is implemented as a 
        /// recursive property.
        /// 
        private bool ShouldSerializeVisible() {
            return flags[invisible]; 
        }
 
 
        /// 
        ///     Gets the unique, hierarchically-qualified identifier for 
        ///       a control. This is different from the ID property, in that the fully-qualified
        ///       identifier includes the identifier for the control's naming container.
        /// 
        [ 
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), 
        WebSysDescription(SR.Control_UniqueID) 
        ]
        public virtual string UniqueID { 
            get {
                if (_cachedUniqueID != null) {
                    return _cachedUniqueID;
                } 

                Control namingContainer = NamingContainer; 
                if (namingContainer != null) { 
                    // if the ID is null at this point, we need to have one created and the control added to the
                    // naming container. 
                    if (_id == null) {
                        GenerateAutomaticID();
                    }
 
                    if (Page == namingContainer) {
                        _cachedUniqueID = _id; 
                    } 
                    else {
                        string uniqueIDPrefix = namingContainer.GetUniqueIDPrefix(); 
                        if (uniqueIDPrefix.Length == 0) {
                            // In this case, it is probably a naming container that is not sited, so we don't want to cache it
                            return _id;
                        } 
                        else {
                            _cachedUniqueID = uniqueIDPrefix + _id; 
                        } 
                    }
 
                    return _cachedUniqueID;
                }
                else {
                    // no naming container 
                    return _id;
                } 
            } 
        }
 
        [SuppressMessage("Microsoft.Naming", "CA1709:IdentifiersShouldBeCasedCorrectly", MessageId = "ID", Justification="This is consistent with UniqueID")]
        [SuppressMessage("Microsoft.Naming", "CA1706:ShortAcronymsShouldBeUppercase", MessageId = "Member", Justification="This is consistent with UniqueID")]
        public string GetUniqueIDRelativeTo(Control control) {
            if (control == null) { 
                throw new ArgumentNullException("control");
            } 
 
            if (!IsDescendentOf(control.NamingContainer)) {
                throw new InvalidOperationException(SR.GetString(SR.Control_NotADescendentOfNamingContainer, control.ID)); 
            }

            if (control.NamingContainer == Page) {
                return UniqueID; 
            } else {
                return UniqueID.Substring(control.NamingContainer.UniqueID.Length + 1); // add 1 for the ID seperator (which is a char) 
            } 
        }
 
        /// 
        ///    Occurs when the control binds to a data source. Notifies the control to perform any data binding during this event.
        /// 
        [ 
        WebCategory("Data"),
        WebSysDescription(SR.Control_OnDataBind) 
        ] 
        public event EventHandler DataBinding {
            add { 
                Events.AddHandler(EventDataBinding, value);
            }
            remove {
                Events.RemoveHandler(EventDataBinding, value); 
            }
        } 
 

        ///  
        ///    Occurs when the control is initialized, the first step in the page lifecycle. Controls should
        ///       perform any initialization steps that are required to create and set up an
        ///       instantiation.
        ///  
        [
        WebSysDescription(SR.Control_OnInit) 
        ] 
        public event EventHandler Init {
            add { 
                Events.AddHandler(EventInit, value);
            }
            remove {
                Events.RemoveHandler(EventInit, value); 
            }
        } 
 

        ///  
        /// Occurs when the control is loaded to the  object. Notifies the control to perform any steps that
        ///    need to occur on each page request.
        /// 
        [ 
        WebSysDescription(SR.Control_OnLoad)
        ] 
        public event EventHandler Load { 
            add {
                Events.AddHandler(EventLoad, value); 
            }
            remove {
                Events.RemoveHandler(EventLoad, value);
            } 
        }
 
 
        /// 
        ///    Occurs when the control is about to render. Controls 
        ///       should perform any pre-rendering steps necessary before saving view state and
        ///       rendering content to the  object.
        /// 
        [ 
        WebSysDescription(SR.Control_OnPreRender)
        ] 
        public event EventHandler PreRender { 
            add {
                Events.AddHandler(EventPreRender, value); 
            }
            remove {
                Events.RemoveHandler(EventPreRender, value);
            } 
        }
 
 
        /// 
        ///    Occurs when the control is unloaded from memory. Controls should perform any 
        ///       final cleanup before this instance of it is 
        /// 
        [
        WebSysDescription(SR.Control_OnUnload) 
        ]
        public event EventHandler Unload { 
            add { 
                Events.AddHandler(EventUnload, value);
            } 
            remove {
                Events.RemoveHandler(EventUnload, value);
            }
        } 

        ///  
        /// Apply stylesheet skin on the control. 
        /// 
        [ 
        EditorBrowsable(EditorBrowsableState.Advanced),
        ]
        public virtual void ApplyStyleSheetSkin(Page page) {
            // Nothing to do if the control is not in a Page. 
            if (page == null) {
                return; 
            } 

            // Only apply stylesheet if not already applied. 
            if (flags[styleSheetApplied]) {
                throw new InvalidOperationException(SR.GetString(SR.StyleSheetAreadyAppliedOnControl));
            }
 
            if (page.ApplyControlStyleSheet(this)) {
                flags.Set(styleSheetApplied); 
            } 
        }
 
        /// 
        /// Apply theme on the control.
        /// 
        private void ApplySkin(Page page) { 
            if (page == null) {
                throw new ArgumentNullException("page"); 
            } 

            if (flags[themeApplied]) { 
                return;
            }

            if (ThemeableAttribute.IsTypeThemeable(this.GetType())) { 
                page.ApplyControlSkin(this);
                flags.Set(themeApplied); 
            } 
        }
 

        /// 
        /// Raises the  event. This
        ///    notifies a control to perform any data binding logic that is associated with it. 
        /// 
        protected virtual void OnDataBinding(EventArgs e) { 
            if(HasEvents()) { 
                EventHandler handler = _events[EventDataBinding] as EventHandler;
                if(handler != null) { 
                    handler(this, e);
                }
            }
        } 

 
        ///  
        ///     Causes data binding to occur on the invoked control and all of its child
        ///       controls. 
        /// 
        public virtual void DataBind() {
            DataBind(true);
        } 

        ///  
        ///     Causes the invoked controls' context to be pushed on the stack, 
        ///       then conditionally call OnDataBinging on the invoked control, and databind all of its child
        ///       controls.  A control would call this with false if it overrides DataBind without calling 
        ///       Control.DataBind, but still wants to be an IDataItemContainer.  FormView and DetailsView
        ///       are good examples of this.
        /// 
        protected virtual void DataBind(bool raiseOnDataBinding) { 
            bool inDataBind = false;
 
            if (IsBindingContainer) { 
                bool foundDataItem;
 
                object dataItem = DataBinder.GetDataItem(this, out foundDataItem);

                if (foundDataItem && (Page != null)) {
                    Page.PushDataBindingContext(dataItem); 
                    inDataBind = true;
                } 
            } 
            try {
                if (raiseOnDataBinding) { 
                    // Do our own databinding
                    OnDataBinding(EventArgs.Empty);
                }
 
                // Do all of our children's databinding
                DataBindChildren(); 
            } 
            finally {
                if (inDataBind) { 
                    Page.PopDataBindingContext();
                }
            }
        } 

 
        ///  
        ///  Causes data binding to occur on all of the child controls.
        ///  
        protected virtual void DataBindChildren() {
            if (HasControls()) {
                string oldmsg = _controls.SetCollectionReadOnly(SR.Parent_collections_readonly);
 
                try {
                    try { 
                        int controlCount = _controls.Count; 
                        for (int i=0; i < controlCount; i++)
                            _controls[i].DataBind(); 
                    }
                    finally {
                        _controls.SetCollectionReadOnly(oldmsg);
                    } 
                }
                catch { 
                    throw; 
                }
            } 
        }

        [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
        internal void PreventAutoID() { 
            // controls that are also naming containers must always get an id
            if (flags[isNamingContainer] == false) { 
                flags.Set(idNotRequired); 
            }
        } 


        /// 
        ///    Notifies the control that an element, XML or HTML, was parsed, and adds it to 
        ///       the control.
        ///  
        [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")] 
        protected virtual void AddParsedSubObject(object obj) {
            Control control = obj as Control; 
            if (control != null) {
                Controls.Add(control);
            }
        } 

        private void UpdateNamingContainer(Control namingContainer) { 
            // Remove the cached uniqueID if the control already had a namingcontainer 
            // and the namingcontainer is changed.
            if (_namingContainer == null || (_namingContainer != null && _namingContainer != namingContainer)) { 
                ClearCachedUniqueIDRecursive();
            }

            // No need to clear the cache if never been initialized 
            if (EffectiveClientIDModeValue != ClientIDMode.Inherit) {
                ClearCachedClientID(); 
                ClearEffectiveClientIDMode(); 
            }
 
            _namingContainer = namingContainer;
        }

        private void ClearCachedUniqueIDRecursive() { 
            _cachedUniqueID = null;
 
            if (_occasionalFields != null) { 
                _occasionalFields.UniqueIDPrefix = null;
            } 

            if (_controls != null) {
                int controlCount = _controls.Count;
                for (int i = 0; i < controlCount; i++) { 
                    _controls[i].ClearCachedUniqueIDRecursive();
                } 
            } 
        }
 
        protected void EnsureID() {
            if (_namingContainer != null) {
                if (_id == null) {
                    GenerateAutomaticID(); 
                }
                flags.Set(mustRenderID); 
            } 
        }
 
        private void GenerateAutomaticID() {
            Debug.Assert(_namingContainer != null);
            Debug.Assert(_id == null);
 
            // Remember that a generated ID is used for this control.
            flags.Set(useGeneratedID); 
 
            // Calculate the automatic ID. For performance and memory reasons
            // we look up a static table entry if possible 
            _namingContainer.EnsureOccasionalFields();
            int idNo = _namingContainer._occasionalFields.NamedControlsID++;
            if (EnableLegacyRendering) {
                // VSWhidbey 517118 
                _id = automaticLegacyIDPrefix + idNo.ToString(NumberFormatInfo.InvariantInfo);
            } 
            else { 
                if (idNo < automaticIDCount) {
                    _id = automaticIDs[idNo]; 
                }
                else {
                    _id = automaticIDPrefix + idNo.ToString(NumberFormatInfo.InvariantInfo);
                } 
            }
 
            _namingContainer.DirtyNameTable(); 
        }
 
        internal virtual string GetUniqueIDPrefix() {
            EnsureOccasionalFields();

            if (_occasionalFields.UniqueIDPrefix == null) { 
                string uniqueID = UniqueID;
                if (!String.IsNullOrEmpty(uniqueID)) { 
                    _occasionalFields.UniqueIDPrefix = uniqueID + IdSeparator; 
                }
                else { 
                    _occasionalFields.UniqueIDPrefix = String.Empty;
                }
            }
 
            return _occasionalFields.UniqueIDPrefix;
        } 
 
        /// 
        /// Raises the  event. This notifies the control to perform 
        ///    any steps necessary for its creation on a page request.
        /// 
        protected internal virtual void OnInit(EventArgs e) {
            if(HasEvents()) { 
                EventHandler handler = _events[EventInit] as EventHandler;
                if(handler != null) { 
                    handler(this, e); 
                }
            } 
        }

        internal virtual void InitRecursive(Control namingContainer) {
            ResolveAdapter(); 
            if (_controls != null) {
                if (flags[isNamingContainer]) { 
                    namingContainer = this; 
                }
                string oldmsg = _controls.SetCollectionReadOnly(SR.Parent_collections_readonly); 

                int controlCount = _controls.Count;
                for (int i = 0; i < controlCount; i++) {
                    Control control = _controls[i]; 

                    // Propagate the page and namingContainer 
                    control.UpdateNamingContainer(namingContainer); 

                    if ((control._id == null) && (namingContainer != null) && !control.flags[idNotRequired]) { 
                        control.GenerateAutomaticID();
                    }
                    control._page = Page;
 
                    control.InitRecursive(namingContainer);
                } 
                _controls.SetCollectionReadOnly(oldmsg); 

            } 

            // Only make the actual call if it hasn't already happened (ASURT 111303)
            if (_controlState < ControlState.Initialized) {
                _controlState = ControlState.ChildrenInitialized; // framework also initialized 

                if ((Page != null) && !DesignMode) { 
                    if (Page.ContainsTheme && EnableTheming) { 
                        ApplySkin(Page);
                    } 
                }

                if (AdapterInternal != null) {
                    AdapterInternal.OnInit(EventArgs.Empty); 
                }
                else { 
                    OnInit(EventArgs.Empty); 
                }
 
                _controlState = ControlState.Initialized;
            }

            // track all subsequent state changes 
            TrackViewState();
 
#if DEBUG 
            ControlInvariant();
#endif 
        }

#if DEBUG
 
        /// 
        ///    This should be used to assert internal state about the control 
        ///  
        internal void ControlInvariant() {
 
            // If the control is initialized, the naming container and page should have been pushed in
            if (_controlState >= ControlState.Initialized) {
                if (DesignMode) {
                    // Top-level UserControls do not have a page or a naming container in the designer 
                    // hence the special casing.
 
                    Debug.Assert((_namingContainer != null) || (this is Page) || (this is UserControl)); 

                    // 



                } 
                else {
                    if (!(this is Page)) { 
                        Debug.Assert(_namingContainer != null); 
                    }
                    Debug.Assert(Page != null); 
                }
            }
            // If naming container is set and the name table exists, the ID should exist in it.
 
            if(_namingContainer != null &&
               _namingContainer._occasionalFields != null && 
               _namingContainer._occasionalFields.NamedControls != null && 
               _id != null) {
                Debug.Assert(_namingContainer._occasionalFields.NamedControls.Contains(_id)); 
            }
        }

        // Collect some statistic about the number of controls with occasional and 
        // rare fields.
        internal void GetRareFieldStatistics(ref int totalControls, 
            ref int withOccasionalFields, ref int withRareFields) { 
            totalControls++;
            if (_occasionalFields != null) { 
                withOccasionalFields++;
                if (_occasionalFields.RareFields != null)
                    withRareFields++;
 
                // No children: we're done
                if (_controls == null) 
                    return; 

                int controlCount = _controls.Count; 
                for (int i = 0; i < controlCount; i++) {
                    Control control = _controls[i];

                    control.GetRareFieldStatistics(ref totalControls, ref withOccasionalFields, 
                        ref withRareFields);
                } 
            } 
        }
#endif 

        protected void ClearChildState() {
            ClearChildControlState();
            ClearChildViewState(); 
        }
 
        protected void ClearChildControlState() { 
            //VSWhidbey 242621 to be consistent with ClearChildViewState, ignore calls before and during Init
            if (ControlState < ControlState.Initialized) { 
                return;
            }
            flags.Set(disableChildControlState);
            if (Page != null) { 
                Page.RegisterRequiresClearChildControlState(this);
            } 
        } 

 
        /// 
        ///    Deletes the view state information for all of the current control's child
        ///       controls.
        ///  
        protected void ClearChildViewState() {
            if(_occasionalFields != null) { 
                _occasionalFields.ControlsViewState = null; 
            }
        } 

        [SuppressMessage("Microsoft.Naming", "CA1706:ShortAcronymsShouldBeUppercase", MessageId="Member")]
        protected void ClearEffectiveClientIDMode() {
            EffectiveClientIDModeValue = ClientIDMode.Inherit; 
            if (HasControls()) {
                foreach (Control control in Controls) { 
                    control.ClearEffectiveClientIDMode(); 
                }
            } 
        }

        [SuppressMessage("Microsoft.Naming", "CA1706:ShortAcronymsShouldBeUppercase", MessageId="Member")]
        protected void ClearCachedClientID() { 
            _cachedPredictableID = null;
            if (HasControls()) { 
                foreach (Control control in Controls) { 
                    control.ClearCachedClientID();
                } 
            }
        }

        ///  
        ///    Indicates whether the current control's children have any saved view state
        ///       information. This property is read-only. 
        ///  
        protected bool HasChildViewState {
            get { 
                return ((_occasionalFields != null) &&
                        (_occasionalFields.ControlsViewState != null) &&
                        (_occasionalFields.ControlsViewState.Count > 0));
            } 
        }
 
 
        /// 
        /// Sets initial focus on the control 
        /// 
        public virtual void Focus() {
            Page.SetFocus(this);
        } 

        internal void LoadControlStateInternal(object savedStateObj) { 
            // Do not load the control state if it has been applied. 
            if (flags[controlStateApplied]) {
                return; 
            }

            flags.Set(controlStateApplied);
 
            Pair savedState = (Pair)savedStateObj;
            if (savedState == null) { 
                return; 
            }
            Page page = Page; 
            if (page != null && !page.ShouldLoadControlState(this)) {
                return;
            }
            // VSWhidbey160650: Only call LoadControlState with non null savedState 
            if (savedState.First != null) {
                LoadControlState(savedState.First); 
            } 
            // VSWhidbey356804: Only call LoadAdapterControlState with non null savedState
            if (AdapterInternal == null || savedState.Second == null) { 
                return;
            }
            AdapterInternal.LoadAdapterControlState(savedState.Second);
        } 

 
        ///  
        /// Load the control state, which is the essential state information needed even if view state is disabled.
        ///  
        protected internal virtual void LoadControlState(object savedState) {
        }

 
        /// 
        ///    Restores the view state information from a previous page 
        ///       request that was saved by the Control.SavedState method. 
        /// 
        protected virtual void LoadViewState(object savedState) { 
            if (savedState != null) {
                ViewState.LoadViewState(savedState);

                // Load values cached out of view state 
                object visible = ViewState["Visible"];
                if (visible != null) { 
                    if(!(bool)visible) { 
                        flags.Set(invisible);
                    } 
                    else {
                        flags.Clear(invisible);
                    }
                    flags.Set(visibleDirty); 
                }
            } 
        } 

        internal void LoadViewStateRecursive(object savedState) { 
            // nothing to do if we have no state
            if (savedState == null || flags[disableViewState])
                return;
 
            if (Page != null && Page.IsPostBack) {
                object controlState = null; 
                object adapterState = null; 
                ArrayList childState = null;
 
                Pair allSavedState = savedState as Pair;
                if (allSavedState != null) {
                    controlState = allSavedState.First;
                    childState = (ArrayList)allSavedState.Second; 
                }
                else { 
                    Debug.Assert(savedState is Triplet); 
                    Triplet t = (Triplet)savedState;
 
                    controlState = t.First;
                    adapterState = t.Second;
                    childState = (ArrayList)t.Third;
                } 

                try { 
                    if ((adapterState != null) && (AdapterInternal != null)) { 
                        AdapterInternal.LoadAdapterViewState(adapterState);
                    } 

                    if (controlState != null) {
                        LoadViewState(controlState);
                    } 

                    if (childState != null) { 
                        if (LoadViewStateByID) { 
                            LoadChildViewStateByID(childState);
                        } 
                        else {
                            LoadChildViewStateByIndex(childState);
                        }
                    } 
                }
                catch (InvalidCastException) { 
                    // catch all viewstate loading problems with casts.  They are most likely changed control trees. 
                    throw new HttpException(SR.GetString(SR.Controls_Cant_Change_Between_Posts));
                } 
                catch (IndexOutOfRangeException) {
                    // catch all viewstate loading problems with indeces.  They are most likely changed control trees.
                    throw new HttpException(SR.GetString(SR.Controls_Cant_Change_Between_Posts));
                } 
            }
 
            _controlState = ControlState.ViewStateLoaded; 
        }
 
        internal void LoadChildViewStateByID(ArrayList childState) {
            int childStateCount = childState.Count;
            for (int i = 0; i < childStateCount; i += 2) {
                // first element is index or ID of control with state and the 
                // next element is state of the control
                string controlId = (string)childState[i]; 
                object state = childState[i + 1]; 

                Control childControl = FindControl(controlId); 
                if (childControl != null) {
                    childControl.LoadViewStateRecursive(state);
                }
                else { 
                    // couldn't find a control for this state blob, save it for later
                    EnsureOccasionalFields(); 
                    if (_occasionalFields.ControlsViewState == null) { 
                        _occasionalFields.ControlsViewState = new Hashtable();
                    } 
                    _occasionalFields.ControlsViewState[controlId] = state;
                }
            }
        } 

        internal void LoadChildViewStateByIndex(ArrayList childState) { 
            ControlCollection ctrlColl = Controls; 
            int ctrlCount = ctrlColl.Count;
 
            int childStateCount = childState.Count;
            for (int i = 0; i < childStateCount; i += 2) {
                // first element is index of control with state and the
                // next element is state of the control 
                int controlIndex = (int)childState[i];
                object state = childState[i + 1]; 
 
                if (controlIndex < ctrlCount) {
                    // we have a control for this state blob 
                    ctrlColl[controlIndex].LoadViewStateRecursive(state);
                }
                else {
                    // couldn't find a control for this state blob, save it for later 
                    EnsureOccasionalFields();
                    if (_occasionalFields.ControlsViewState == null) { 
                        _occasionalFields.ControlsViewState = new Hashtable(); 
                    }
                    _occasionalFields.ControlsViewState[controlIndex] = state; 
                }
            }
        }
 
        ///
        /// Figure out if a path is physical or virtual.  This is useful because a number of our controls 
        /// accept either type of path for the same attribute. 
        ///
        internal void ResolvePhysicalOrVirtualPath(string path, out VirtualPath virtualPath, out string physicalPath) { 
            if (System.Web.Util.UrlPath.IsAbsolutePhysicalPath(path)) {
                physicalPath = path;
                virtualPath = null;
            } 
            else {
                physicalPath = null; 
 
                // It could be relative, so resolve it
                virtualPath = TemplateControlVirtualDirectory.Combine(VirtualPath.Create(path)); 
            }
        }

 
        /// 
        ///  
        ///   This function takes a virtual path, that is a relative or root relative URL without a protocol. 
        ///   It returns the mapped physcial file name relative to the template source. It throws an exception if
        ///   there is insufficient security access to read or investigate the mapped result. This should be used 
        ///   by controls that can read files and live in fully trusted DLLs such as System.Web.dll to prevent
        ///   security issues. The exception thrown does not give away information about the mapping.  For absolute
        ///   physical paths, this function checks permission
        ///  
        /// 
        protected internal string MapPathSecure(string virtualPath) { 
            if (String.IsNullOrEmpty(virtualPath)) { 
                throw new ArgumentNullException("virtualPath", SR.GetString(SR.VirtualPath_Length_Zero));
            } 

            string physicalPath;
            VirtualPath virtualPathObject;
            ResolvePhysicalOrVirtualPath(virtualPath, out virtualPathObject, out physicalPath); 
            if (physicalPath == null) {
                physicalPath = virtualPathObject.MapPathInternal(TemplateControlVirtualDirectory, 
                    true /*allowCrossAppMapping*/); 
            }
 
            // Security check
            HttpRuntime.CheckFilePermission(physicalPath);

            return physicalPath; 
        }
 
 
        /// 
        ///  
        ///   This function takes a virtual path, that is a relative or root relative URL without a protocol.
        ///   It can also take a physical path, either local (c:\) or UNC.
        ///   It returns a stream used to read to contents of the file. It throws an exception if
        ///   there is insufficient security access to read or investigate the mapped result. This should be used 
        ///   by controls that can read files and live in fully trusted DLLs such as System.Web.dll to prevent
        ///   security issues. The exception thrown does not give away information about the mapping.  For absolute 
        ///   physical paths, this function checks permission 
        /// 
        ///  
        protected internal Stream OpenFile(string path) {

            string physicalPath = null;
            VirtualFile vfile = null; 

            // Need to Trim it since MapPath no longer allows trailing space (VSWhidbey 441210) 
            path = path.Trim(); 

            if (UrlPath.IsAbsolutePhysicalPath(path)) { 
                // Absolute physical path
                physicalPath = path;
            }
            else { 
                vfile = HostingEnvironment.VirtualPathProvider.GetFile(path);
                MapPathBasedVirtualFile mapPathVFile = vfile as MapPathBasedVirtualFile; 
                if (mapPathVFile != null) { 
                    physicalPath = mapPathVFile.PhysicalPath;
                } 
            }

            // If we got a physical path, make sure the user has access to it
            if (physicalPath != null) { 
                HttpRuntime.CheckFilePermission(physicalPath);
            } 
 
            if (vfile != null) {
                return vfile.Open(); 
            }
            else {
                return new FileStream(physicalPath, FileMode.Open, FileAccess.Read, FileShare.Read);
            } 
        }
 
        /// 
        /// Open a stream from either a virtual or physical path, and if possible get a CacheDependency
        /// for the resulting Stream. 
        ///
        internal Stream OpenFileAndGetDependency(VirtualPath virtualPath, string physicalPath, out CacheDependency dependency) {

            // Only one of the paths should be non-null 
            Debug.Assert((virtualPath == null) != (physicalPath == null));
 
            // If we got a virtual path, and we're using the default VPP, call MapPath 
            if (physicalPath == null && HostingEnvironment.UsingMapPathBasedVirtualPathProvider) {
                physicalPath = virtualPath.MapPathInternal(TemplateControlVirtualDirectory, 
                    true /*allowCrossAppMapping*/);
            }

            Stream stream; 
            if (physicalPath != null) {
                // Security check 
                HttpRuntime.CheckFilePermission(physicalPath); 

                // Work directly with the physical file, bypassing the VPP 
                stream = new FileStream(physicalPath, FileMode.Open, FileAccess.Read, FileShare.Read);
                dependency = new CacheDependency(0, physicalPath);
            }
            else { 
                // It's non file system based, so go though the VirtualPathProvider
                stream = virtualPath.OpenFile(); 
                dependency = VirtualPathProvider.GetCacheDependency(virtualPath); 
            }
 
            return stream;
        }

 
        /// 
        /// Raises the  
        /// event. This notifies the control that it should perform any work that needs to 
        /// occur for each page request.
        ///  
        protected internal virtual void OnLoad(EventArgs e) {
            if(HasEvents()) {
                EventHandler handler = _events[EventLoad] as EventHandler;
                if(handler != null) { 
                    handler(this, e);
                } 
            } 
        }
 
        internal virtual void LoadRecursive() {

            // Only make the actual call if it hasn't already happened (ASURT 111303)
            if (_controlState < ControlState.Loaded) { 
                if (AdapterInternal != null) {
                    AdapterInternal.OnLoad(EventArgs.Empty); 
                } 
                else {
                    OnLoad(EventArgs.Empty); 
                }
            }

            // Call Load on all our children 
            if (_controls != null) {
                string oldmsg = _controls.SetCollectionReadOnly(SR.Parent_collections_readonly); 
 
                int controlCount = _controls.Count;
                for (int i = 0; i < controlCount; i++) { 
                    _controls[i].LoadRecursive();
                }

                _controls.SetCollectionReadOnly(oldmsg); 
            }
 
            if (_controlState < ControlState.Loaded) 
                _controlState = ControlState.Loaded;
        } 


        /// 
        /// Raises the  event. This method uses event arguments 
        ///    to pass the event data to the control.
        ///  
        protected internal virtual void OnPreRender(EventArgs e) { 
            if(HasEvents()) {
                EventHandler handler = _events[EventPreRender] as EventHandler; 
                if (handler != null) {
                    handler(this, e);
                }
            } 
        }
 
        internal virtual void PreRenderRecursiveInternal() { 
            // Call Visible property and cache value in !flags[invisible] to allow Visible to be overridden.
            // This avoids unnecessary virtual property calls in SaveViewState and Render. 
            bool visible = Visible;
            if(!visible) {
                flags.Set(invisible);
            } 
            else {
                flags.Clear(invisible); 
                EnsureChildControls(); 

                if (AdapterInternal != null) { 
                    AdapterInternal.OnPreRender(EventArgs.Empty);
                }
                else {
                    OnPreRender(EventArgs.Empty); 
                }
 
                if (_controls != null) { 
                    string oldmsg = _controls.SetCollectionReadOnly(SR.Parent_collections_readonly);
 
                    int controlCount = _controls.Count;
                    for (int i=0; i < controlCount; i++) {
                        _controls[i].PreRenderRecursiveInternal();
                    } 
                    _controls.SetCollectionReadOnly(oldmsg);
                } 
            } 
            _controlState = ControlState.PreRendered;
        } 

        internal int EstimateStateSize(object state) {
            if(state == null) {
                return 0; 
            }
            return Util.SerializeWithAssert(new ObjectStateFormatter(), state).Length; 
        } 

        /* 
         * Walk the tree and fill in profile information
         */

        ///  
        /// 
        /// Gathers information about the control and delivers it to the  
        /// property to be displayed when tracing is enabled for the page. 
        /// 
        protected void BuildProfileTree(string parentId, bool calcViewState) { 
            // estimate the viewstate size.
            calcViewState = calcViewState && (!flags[disableViewState]);
            int viewstatesize;
            if (calcViewState) 
                viewstatesize = EstimateStateSize(SaveViewState());
            else 
                viewstatesize = 0; 

            int controlstatesize = 0; 
            if(Page != null && Page._registeredControlsRequiringControlState != null && Page._registeredControlsRequiringControlState.Contains(this)) {
                controlstatesize = EstimateStateSize(SaveControlStateInternal());
            }
 
            // give it all to the profiler
            Page.Trace.AddNewControl(UniqueID, parentId, this.GetType().FullName, viewstatesize, controlstatesize); 
 
            if (_controls != null) {
                int controlCount = _controls.Count; 
                for (int i = 0; i < controlCount; i++) {
                    _controls[i].BuildProfileTree(UniqueID, calcViewState);
                }
            } 
        }
 
 
        internal object SaveControlStateInternal() {
            object controlState = SaveControlState(); 
            object adapterControlState = null;
            if (AdapterInternal != null) {
                adapterControlState = AdapterInternal.SaveAdapterControlState();
            } 
            if (controlState != null || adapterControlState != null) {
                return new Pair(controlState, adapterControlState); 
            } 
            return null;
        } 


        /// 
        /// Save the control state, which is the essential state information needed even if view state is disabled. 
        /// 
        protected internal virtual object SaveControlState() { 
            return null; 
        }
 
        // Save modified state the control would like restored on the postback.
        // Return null if there is no state to save.

        ///  
        ///    
        ///       Saves view state for use with a later  
        ///       request. 
        ///    
        ///  
        protected virtual object SaveViewState() {
            // Save values cached out of view state
            if (flags[visibleDirty]) {
                ViewState["Visible"] = !flags[invisible]; 
            }
            if (_viewState != null) 
                return _viewState.SaveViewState(); 

            return null; 
        }

        // Answer any state this control or its descendants want to save on freeze.
        // The format for saving is Triplet(myState, ArrayList childIDs, ArrayList childStates), 
        // where myState or childStates and childIDs may be null.
        internal object SaveViewStateRecursive(ViewStateMode inheritedMode) { 
            if (flags[disableViewState]) 
                return null;
 
            bool saveThisState;
            if (flags[viewStateNotInherited]) {
                if (flags[viewStateMode]) {
                    saveThisState = true; 
                    inheritedMode = ViewStateMode.Enabled;
                } 
                else { 
                    saveThisState = false;
                    inheritedMode = ViewStateMode.Disabled; 
                }
            }
            else {
                saveThisState = (inheritedMode == ViewStateMode.Enabled); 
            }
 
            object adapterState = null; 
            object controlSavedState = null;
 
            if (saveThisState) {
                if (AdapterInternal != null) {
                    adapterState = AdapterInternal.SaveAdapterViewState();
                } 
                controlSavedState = SaveViewState();
            } 
 
            ArrayList childStates = null;
            if (HasControls()) { 
                ControlCollection occasionalFieldControls = _controls;
                int occasionalFieldControlCount = occasionalFieldControls.Count;

                bool useId = LoadViewStateByID; 
                for (int i = 0; i < occasionalFieldControlCount; i++) {
                    Control child = occasionalFieldControls[i]; 
                    object childState = child.SaveViewStateRecursive(inheritedMode); 
                    if (childState != null) {
                        if (childStates == null) { 
                            childStates = new ArrayList(occasionalFieldControlCount);
                        }

                        if (useId) { 
                            child.EnsureID();
                            childStates.Add(child.ID); 
                        } 
                        else {
                            childStates.Add(i); 
                        }
                        childStates.Add(childState);
                    }
                } 
            }
 
            if (AdapterInternal != null) { 
                if ((controlSavedState != null) || (adapterState != null) || (childStates != null)) {
                    return new Triplet(controlSavedState, adapterState, childStates); 
                }
            }
            else {
                if ((controlSavedState != null) || (childStates != null)) { 
                    return new Pair(controlSavedState, childStates);
                } 
            } 

            return null; 
        }


        ///  
        /// Outputs control content to a provided HTMLTextWriter
        /// output stream. 
        ///  
        protected internal virtual void Render(HtmlTextWriter writer) {
            RenderChildren(writer); 
        }

        internal void RenderChildrenInternal(HtmlTextWriter writer, ICollection children) {
            // If we have a delegate, use it for the rendering. 
            // This happens when there is some ASP code.  See also Whidbey 33012.
            if(RareFields != null && RareFields.RenderMethod != null ) { 
                writer.BeginRender(); 
                RareFields.RenderMethod(writer, this);
                writer.EndRender(); 
                return;
            }
            if (children != null) {
                foreach (Control child in children) { 
                    child.RenderControl(writer);
                } 
            } 
        }
 
        protected internal virtual void RenderChildren(HtmlTextWriter writer) {
            ICollection children = _controls;
            RenderChildrenInternal(writer, children);
        } 

        ///  
        ///    [To be supplied.] 
        /// 
        [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")] 
        public virtual void RenderControl(HtmlTextWriter writer) {
            //use the Adapter property to ensure it is resolved
            RenderControl(writer, Adapter);
        } 

        ///  
        ///    Used for MobilePage implementation. 
        /// 
        protected void RenderControl(HtmlTextWriter writer, ControlAdapter adapter) { 
            if (!flags[invisible] && !flags[notVisibleOnPage]) {
                HttpContext context = (Page == null) ? null : Page._context;
                if (context  != null && context.TraceIsEnabled) {
                    int presize = context.Response.GetBufferedLength(); 
                    RenderControlInternal(writer, adapter);
                    int postsize = context.Response.GetBufferedLength(); 
                    context.Trace.AddControlSize(UniqueID, postsize - presize); 
                }
                else { 
                    RenderControlInternal(writer, adapter);
                }
            }
        } 

        private void RenderControlInternal(HtmlTextWriter writer, ControlAdapter adapter) { 
            if (adapter != null) { 
                //
                adapter.BeginRender(writer); 
                adapter.Render(writer);
                adapter.EndRender(writer);
            }
            else { 
                Render(writer);
            } 
        } 

 
        /// 
        ///    [To be supplied.]
        /// 
        protected internal virtual void OnUnload(EventArgs e) { 
            if(HasEvents()) {
                EventHandler handler = _events[EventUnload] as EventHandler; 
                if (handler != null) { 
                    handler(this, e);
                } 
            }
        }

 
        /// 
        ///    Enables a control to perform final cleanup. 
        ///  
        public virtual void Dispose() {
            IContainer container = null; 

            if (Site != null) {
                container = (IContainer)Site.GetService(typeof(IContainer));
                if (container != null) { 
                    container.Remove(this);
                    EventHandler disp = Events[EventDisposed] as EventHandler; 
                    if (disp != null) 
                        disp(this, EventArgs.Empty);
                } 
            }

            if (_occasionalFields != null) {
                _occasionalFields.Dispose(); 
                //do not null out for backwards compat, VSWhidbey 475940
                //_occasionalFields = null; 
            } 

            if (_events != null) { 
                _events.Dispose();
                _events = null;
            }
        } 

 
        internal virtual void UnloadRecursive(bool dispose) { 
            Page page = Page;
            if (page != null && page.RequiresControlState(this)) { 
                page.UnregisterRequiresControlState(this);
                RareFieldsEnsured.RequiredControlState = true;
            }
 
            // Remove the generated ID so it will be assigned a different ID next time.
            if (flags[useGeneratedID]) { 
                _id = null; 
                flags.Clear(useGeneratedID);
            } 

            if (_controls != null) {
                string oldmsg = _controls.SetCollectionReadOnly(SR.Parent_collections_readonly);
 
                int controlCount = _controls.Count;
                for (int i = 0; i < controlCount; i++) 
                    _controls[i].UnloadRecursive(dispose); 

                _controls.SetCollectionReadOnly(oldmsg); 
            }

            if (AdapterInternal != null) {
                AdapterInternal.OnUnload(EventArgs.Empty); 
            }
            else { 
                OnUnload(EventArgs.Empty); 
            }
 
            //
            if (dispose)
                Dispose();
 
            // VSWhidbey 244999: Everett behavior doesn't reset the control state.
            // But for control which requires its OnInit method to be called again 
            // to properly initialize when the control is removed and added back 
            // to Page's control tree, the control can override IsReloadable
            // to true so the control state is reset.  e.g. Validator, see bug 
            if (IsReloadable) {
                _controlState = ControlState.Constructed;
            }
        } 

 
        ///  
        ///    Assigns an sources of the event and its information up the page control
        ///       hierarchy until they reach the top of the control tree.  
        /// 
        protected void RaiseBubbleEvent(object source, EventArgs args) {
            Control currentTarget = Parent;
            while (currentTarget != null) { 
                if (currentTarget.OnBubbleEvent(source, args)) {
                    return; 
                } 
                currentTarget = currentTarget.Parent;
            } 
        }


        ///  
        ///    Determines whether the event for the control should be passed up the page's
        ///       control hierarchy. 
        ///  
        protected virtual bool OnBubbleEvent(object source, EventArgs args) {
            return false; 
        }


        // Members related to being a container 

 
        ///  
        ///     Gets a ControlCollection object that represents the child controls for a specified control in the
        ///       UI hierarchy. 
        /// 
        [
        Browsable(false),
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden), 
        WebSysDescription(SR.Control_Controls)
        ] 
        public virtual ControlCollection Controls { 
            get {
                if (_controls == null) { 
                    _controls = CreateControlCollection();
                }
                return _controls;
            } 
        }
 
 
        /// 
        ///    Indicates a dictionary of state information that allows you to save and restore 
        ///       the state of a control across multiple requests for the same page.
        /// 
        [
        Browsable(false), 
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden),
        WebSysDescription(SR.Control_State) 
        ] 
        protected virtual StateBag ViewState {
            get { 
                if (_viewState != null) {   // create a StateBag on demand; WebControl makes its case sensitive
                    return _viewState;
                }
 
                _viewState = new StateBag(ViewStateIgnoresCase);
                if (IsTrackingViewState) 
                    _viewState.TrackViewState(); 
                return _viewState;
            } 
        }

        // fast enough that we cam always use it.
 
        /// 
        /// Indicates whether the  object is case-insensitive. 
        ///  
        [
        Browsable(false), 
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)
        ]
        protected virtual bool ViewStateIgnoresCase {
            [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")] 
            get {
                return false; 
            } 
        }
 

        /// 
        /// 
        protected internal virtual void AddedControl(Control control, int index) { 
            if (control.OwnerControl != null) {
                throw new InvalidOperationException(SR.GetString(SR.Substitution_NotAllowed)); 
            } 

            if (control._parent != null) { 
                control._parent.Controls.Remove(control);
            }

            control._parent = this; 
            control._page = Page;
            control.flags.Clear(designModeChecked); 
 
            // We only add to naming container if it is available. Otherwise, it will be pushed through
            // during InitRecursive 
            Control namingContainer = flags[isNamingContainer] ? this : _namingContainer;
            if (namingContainer != null) {
                control.UpdateNamingContainer(namingContainer);
                if (control._id == null && !control.flags[idNotRequired]) { 
                    // this will also dirty the name table in the naming container
                    control.GenerateAutomaticID(); 
                } 
                else if (control._id != null || (control._controls != null)) {
                    // If the control has and ID, or has children (which *may* themselves 
                    // have ID's), we need to dirty the name table (ASURT 100557)
                    namingContainer.DirtyNameTable();
                }
            } 

            /* 
             * The following is for times when AddChild is called after CreateChildControls. This 
             * allows users to add children at any time in the creation process without having
             * to understand the underlying machinery. 
             * Note that if page is null, it means we haven't been attached to a container ourselves.
             * If this is true, when we are, our children will be recursively set up.
             */
            if (_controlState >= ControlState.ChildrenInitialized) { 

                Debug.Assert(namingContainer != null); 
                control.InitRecursive(namingContainer); 

                // VSWhidbey 396372: We need to reregister the control state if the control is reparented because the control 
                // is unregistered during unload, but its already been inited once, so it will not get its Init called again
                // which is where most controls call RegisterRequiresControlState
                if (control._controlState >= ControlState.Initialized &&
                    control.RareFields != null && 
                    control.RareFields.RequiredControlState) {
                    Page.RegisterRequiresControlState(control); 
                } 

                if (_controlState >= ControlState.ViewStateLoaded) { 
                    object viewState = null;
                    if(_occasionalFields != null && _occasionalFields.ControlsViewState != null) {
                        viewState = _occasionalFields.ControlsViewState[index];
                        // This solution takes the conservative approach that once viewstate has been 
                        // applied to a child control, it is thrown away.  This eliminates inadvertently
                        // setting viewstate on the wrong control, which can occur in scenarios where 
                        // the child control collection is being manipulated via code.  Probably need 
                        // to provide a feature where programmer can control whether to reapply viewstate
                        // or not. 
                        if (LoadViewStateByID) {
                            control.EnsureID();
                            viewState = _occasionalFields.ControlsViewState[control.ID];
                            _occasionalFields.ControlsViewState.Remove(control.ID); 
                        }
                        else { 
                            viewState = _occasionalFields.ControlsViewState[index]; 
                            _occasionalFields.ControlsViewState.Remove(index);
                        } 
                    }

                    control.LoadViewStateRecursive(viewState);
 
                    if (_controlState >= ControlState.Loaded) {
                        control.LoadRecursive(); 
 
                        if (_controlState >= ControlState.PreRendered)
                            control.PreRenderRecursiveInternal(); 
                    }
                }
            }
        } 

 
        ///  
        ///    [To be supplied.]
        ///  
        protected virtual ControlCollection CreateControlCollection() {
            return new ControlCollection(this);
        }
 

        ///  
        ///     
        ///       Notifies any controls that use composition-based implementation to create any
        ///       child controls they contain in preperation for postback or rendering. 
        ///    
        /// 
        [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
        protected internal virtual void CreateChildControls() { 
        }
 
 

        ///  
        ///    Indicates whether the control's child controls have been created.
        /// 
        protected bool ChildControlsCreated {
            get { 
                return flags[controlsCreated];
            } 
            set { 
                if (!value && flags[controlsCreated]) {
                    Controls.Clear(); 
                }
                if(value) {
                    flags.Set(controlsCreated);
                } 
                else {
                    flags.Clear(controlsCreated); 
                } 
            }
        } 


        /// 
        ///    Make a URL absolute using the AppRelativeTemplateSourceDirectory.  The returned URL is for 
        ///        client use, and will contain the session cookie if appropriate.
        ///  
        public string ResolveUrl(string relativeUrl) { 
            if (relativeUrl == null) {
                throw new ArgumentNullException("relativeUrl"); 
            }

            // check if its empty or already absolute
            if ((relativeUrl.Length == 0) || (UrlPath.IsRelativeUrl(relativeUrl) == false)) { 
                return relativeUrl;
            } 
 
            string baseUrl = AppRelativeTemplateSourceDirectory;
            if (String.IsNullOrEmpty(baseUrl)) { 
                return relativeUrl;
            }

            // first make it absolute 
            string url = UrlPath.Combine(baseUrl, relativeUrl);
 
            // include the session cookie if available (ASURT 47658) 
            // As a side effect, this will change an app relative path (~/...) to app absolute
            return Context.Response.ApplyAppPathModifier(url); 
        }


        ///  
        ///     Return a URL that is suitable for use on the client.
        ///     If the URL is absolute, return it unchanged.  If it is relative, turn it into a 
        ///     relative URL that is correct from the point of view of the current request path 
        ///     (which is what the browser uses for resolution).
        ///  
        public string ResolveClientUrl(string relativeUrl) {
            if (DesignMode && Page != null && Page.Site != null) {
                IUrlResolutionService resolutionService = (IUrlResolutionService)Page.Site.GetService(typeof(IUrlResolutionService));
                if (resolutionService != null) { 
                    return resolutionService.ResolveClientUrl(relativeUrl);
                } 
            } 

            if (relativeUrl == null) { 
                throw new ArgumentNullException("relativeUrl");
            }

            // Get the app absolute TemplateSourceDirectory (not app relative) 
            string tplSourceDir = VirtualPath.GetVirtualPathString(TemplateControlVirtualDirectory);
            if (String.IsNullOrEmpty(tplSourceDir)) 
                return relativeUrl; 

            string baseRequestDir = Context.Request.ClientBaseDir.VirtualPathString; 

            // If the path is app relative (~/...), we cannot take shortcuts, since
            // the ~ is meaningless on the client, and must be resolved
            if (!UrlPath.IsAppRelativePath(relativeUrl)) { 

                // If the template source directory is the same as the directory of the request, 
                // we don't need to do any adjustments to the input path 
                if (StringUtil.EqualsIgnoreCase(baseRequestDir, tplSourceDir))
                    return relativeUrl; 

                // check if it's empty or absolute
                if ((relativeUrl.Length == 0) || (!UrlPath.IsRelativeUrl(relativeUrl))) {
                    return relativeUrl; 
                }
            } 
 
            // first make it absolute
            string url = UrlPath.Combine(tplSourceDir, relativeUrl); 

            // Make sure the path ends with a slash before calling MakeRelative
            baseRequestDir = UrlPath.AppendSlashToPathIfNeeded(baseRequestDir);
 
            // Now, make it relative to the current request, so that the client will
            // compute the correct path 
            url = HttpUtility.UrlPathEncode(UrlPath.MakeRelative(baseRequestDir, url)); 
            Debug.Trace("ClientUrl", "*** ResolveClientUrl (" + relativeUrl + ") --> " + url + " ***");
            return url; 
        }

        internal void DirtyNameTable() {
            Debug.Assert(this is INamingContainer); 
            if(_occasionalFields != null) {
                _occasionalFields.NamedControls = null; 
            } 
        }
 
        private void EnsureNamedControlsTable() {
            Debug.Assert(this is INamingContainer);
            Debug.Assert(HasControls());
            Debug.Assert(_occasionalFields != null); 
            Debug.Assert(_occasionalFields.NamedControls == null);
 
            _occasionalFields.NamedControls = new HybridDictionary(/*initialSize*/ _occasionalFields.NamedControlsID, /*caseInsensitive*/ true); 
            FillNamedControlsTable(this, _controls);
        } 

        private void FillNamedControlsTable(Control namingContainer, ControlCollection controls) {
            Debug.Assert(namingContainer._occasionalFields != null);
            Debug.Assert(namingContainer._occasionalFields.NamedControls != null); 
            Debug.Assert((controls != null) && (controls.Count != 0));
 
            int controlCount = controls.Count; 
            for (int i=0; i < controlCount; i++) {
                Control control = controls[i]; 
                if (control._id != null) {
#if DEBUG
                    if (control._namingContainer != null) {
                        Debug.Assert(control._namingContainer == namingContainer); 
                    }
#endif // DEBUG 
                    try { 
                        namingContainer.EnsureOccasionalFields();
                        namingContainer._occasionalFields.NamedControls.Add(control._id, control); 
                    }
                    catch {
                        throw new HttpException(SR.GetString(SR.Duplicate_id_used, control._id, "FindControl"));
                    } 
                }
                if (control.HasControls() && (control.flags[isNamingContainer] == false)) { 
                    FillNamedControlsTable(namingContainer, control.Controls); 
                }
            } 
        }


        ///  
        ///    Searches the current naming container for a control with
        ///       the specified  . 
        ///  
        public virtual Control FindControl(String id) {
            return FindControl(id, 0); 
        }


        ///  
        /// 
        ///    Searches the current naming container for a control with the specified 
        ///     and an offset to aid in the 
        ///       search.
        ///  
        protected virtual Control FindControl(String id, int pathOffset) {
            string childID;

            EnsureChildControls(); 

            // If we're not the naming container, let it do the job 
            if (!(flags[isNamingContainer])) { 
                Control namingContainer = NamingContainer;
                if (namingContainer != null) { 
                    return namingContainer.FindControl(id, pathOffset);
                }
                return null;
            } 

            // No registered control, demand create the named controls table 
            //call HasControls doesn't ensures _occasionalFields != null 
            if (HasControls()) {
                EnsureOccasionalFields(); 
                if (_occasionalFields.NamedControls == null) {
                    EnsureNamedControlsTable();
                }
            } 
            if (_occasionalFields == null || _occasionalFields.NamedControls == null) {
                return null; 
            } 

            // Need to support ':' for V1 backward compatibility. 
            char[] findControlSeparators = { ID_SEPARATOR, LEGACY_ID_SEPARATOR };

            // Is it a hierarchical name?
            int newPathOffset = id.IndexOfAny(findControlSeparators, pathOffset); 

            // If not, handle it here 
            if (newPathOffset == -1) { 
                childID = id.Substring(pathOffset);
                return _occasionalFields.NamedControls[childID] as Control; 
            }

            // Get the name of the child, and try to locate it
            childID = id.Substring(pathOffset, newPathOffset - pathOffset); 
            Control child =  _occasionalFields.NamedControls[childID] as Control;
 
            // Child doesn't exist: fail 
            if (child == null)
                return null; 

            return child.FindControl(id, newPathOffset + 1);
        }
 
        /*
         * Called when the controls of a naming container are cleared. 
         */ 
        internal void ClearNamingContainer() {
            Debug.Assert(this is INamingContainer); 

            EnsureOccasionalFields();
            _occasionalFields.NamedControlsID = 0;
            DirtyNameTable(); 
        }
 
 
        /// 
        ///  
        /// 
        [SecurityPermission(SecurityAction.Demand, Unrestricted = true)]
        protected virtual IDictionary GetDesignModeState() {
            ControlRareFields rareFields = RareFieldsEnsured; 
            if (rareFields.DesignModeState == null) {
                rareFields.DesignModeState = new HybridDictionary(); 
            } 
            return rareFields.DesignModeState;
        } 


        /// 
        ///    Determines if the current control contains any child 
        ///       controls. Since this method simply deteremines if any child controls exist at
        ///       all, it can enhance performance by avoiding a call to the Count property, 
        ///       inherited from the  class, on the  
        ///       property.
        ///  
        public virtual bool HasControls() {
            return _controls != null && _controls.Count > 0;
        }
 
        /*
         * Check if a Control either has children or has a compiled render method. 
         * This is to address issues like ASURT 94127 
         */
        internal bool HasRenderingData() { 
            return HasControls() || HasRenderDelegate();
        }

        /* 
         * Check if a Control either has children or has a compiled render method.
         * This is to address issues like ASURT 94127 
         */ 
        internal bool HasRenderDelegate() {
            if(RareFields != null) { 
                return (RareFields.RenderMethod != null );
            }
            return false;
        } 

        /* 
         * Returns true if the container contains just a static string, i.e., 
         * when the Controls collection has a single LiteralControl.
         */ 

        /// 
        ///    Determines if the container holds literal content only.
        ///       When this method returns  
        ///       , the container collection only holds a single literal control. The
        ///       content is then passed to the requesting browser as HTML. 
        ///  
        protected bool IsLiteralContent() {
            return (_controls != null) && (_controls.Count == 1) && 
            ((_controls[0] is LiteralControl));
        }

 
        /// 
        ///    Determines if view state changes to the 
        ///     
        ///    are being saved. 
        ///  
        protected bool IsTrackingViewState {
            get {
                return flags[marked];
            } 
        }
 
 
        /// 
        ///    Turns on tracking of view state changes to the control 
        ///       so that they can be stored in the 
        ///       object.
        /// 
        [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")] 
        protected virtual void TrackViewState() {
            if (_viewState != null) 
                _viewState.TrackViewState(); 

            flags.Set(marked); 
        }


        ///  
        ///    Checks that the control contains child controls; if it does not, it creates
        ///       them. This includes any literal content being parsed as a  
        ///       object.  
        /// 
        protected virtual void EnsureChildControls() { 
            if (!ChildControlsCreated && !flags[creatingControls]) {
                flags.Set(creatingControls);
                try {
                    ResolveAdapter(); 
                    if (AdapterInternal != null) {
                        AdapterInternal.CreateChildControls(); 
                    } 
                    else {
                        CreateChildControls(); 
                    }

                    // Only set ChildControlsCreated = true if CreateChildControls() did not throw
                    // an exception (VSWhidbey 465798). 
                    ChildControlsCreated = true;
                } 
                finally { 
                    flags.Clear(creatingControls);
                } 
            }
        }

        ///  
        /// Used internally to store a ControlBuilder reference for the control.
        /// The builder will be used at design-time to help persist all the filtered properties 
        /// of the control. 
        /// 
        internal void SetControlBuilder(ControlBuilder controlBuilder) { 
            RareFieldsEnsured.ControlBuilder = controlBuilder;
        }

 
        /// 
        ///  
        protected internal virtual void RemovedControl(Control control) { 
            if (control.OwnerControl != null) {
                throw new InvalidOperationException(SR.GetString(SR.Substitution_NotAllowed)); 
            }

            if ((_namingContainer != null) && (control._id != null)) {
                _namingContainer.DirtyNameTable(); 
            }
 
            // Controls may need to do their own cleanup. 
            control.UnloadRecursive(false);
 
            control._parent = null;
            control._page = null;
            control._namingContainer = null;
 
            // Don't reset template source virtual directory on TemplateControl's, because
            // the path is their own, not their parent. i.e. it doesn't change no matter 
            // where in the tree they end up. 
            if (!(control is TemplateControl)) {
                if (control._occasionalFields != null) { 
                    control._occasionalFields.TemplateSourceVirtualDirectory = null;
                }
            }
 
            if (control._occasionalFields != null ) {
                control._occasionalFields.TemplateControl = null; 
            } 

            control.flags.Clear(mustRenderID); 
            control.ClearCachedUniqueIDRecursive();
        }

        internal void SetDesignMode() { 
            flags.Set(designMode);
            flags.Set(designModeChecked); 
        } 

 
        /// 
        /// 
        /// 
        protected virtual void SetDesignModeState(IDictionary data) { 
        }
 
        // Set the delegate to the render method 

        ///  
        /// 
        ///    Assigns any event handler delegates for the control to match the parameters
        ///       defined in the . 
        ///  
        [EditorBrowsable(EditorBrowsableState.Advanced)]
        public void SetRenderMethodDelegate(RenderMethod renderMethod) { 
            RareFieldsEnsured.RenderMethod = renderMethod; 

            // Make the collection readonly if there are code blocks (ASURT 78810) 
            Controls.SetCollectionReadOnly(SR.Collection_readonly_Codeblocks);
        }

 
        /// 
        ///  
        ///    Returns whether the control contains any data binding logic. This method is 
        ///       only accessed by RAD designers.
        ///  
        bool IDataBindingsAccessor.HasDataBindings {
            get {
                return ((RareFields != null) && (RareFields.DataBindings != null) && (RareFields.DataBindings.Count != 0));
            } 
        }
 
 
        /// 
        ///  
        /// Indicates a collection of all data bindings on the control. This property is
        /// read-only.
        /// 
        DataBindingCollection IDataBindingsAccessor.DataBindings { 
            get {
                ControlRareFields rareFields = RareFieldsEnsured; 
                if (rareFields.DataBindings == null) { 
                    rareFields.DataBindings = new DataBindingCollection();
                } 
                return rareFields.DataBindings;
            }
        }
 

        // IParserAccessor interface 
        // A sub-object tag was parsed by the parser; add it to this control. 

        ///  
        /// 
        /// Notifies the control that an element, XML or HTML, was parsed, and adds it to
        /// the control.
        ///  
        [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
        void IParserAccessor.AddParsedSubObject(object obj) { 
            AddParsedSubObject(obj); 
        }
 
        internal string SpacerImageUrl {
            get {
                EnsureOccasionalFields();
                if (_occasionalFields.SpacerImageUrl == null) { 
                    _occasionalFields.SpacerImageUrl = Page.ClientScript.GetWebResourceUrl(typeof(WebControl), "Spacer.gif");
                } 
                return _occasionalFields.SpacerImageUrl; 
            }
        } 

        private Control OwnerControl {
            [System.Runtime.TargetedPatchingOptOut("Performance critical to inline across NGen image boundaries")]
            get { 
                if (RareFields == null) {
                    return null; 
                } 

                return RareFields.OwnerControl; 
            }
            set {
                RareFieldsEnsured.OwnerControl = value;
            } 
        }
 
        internal IPostBackDataHandler PostBackDataHandler { 
            get {
                IPostBackDataHandler pbdh = AdapterInternal as IPostBackDataHandler; 
                if(pbdh != null)
                    return pbdh;
                pbdh = this as IPostBackDataHandler;
                return pbdh; 
            }
        } 
 
        internal IPostBackEventHandler PostBackEventHandler {
            get { 
                IPostBackEventHandler pbeh = AdapterInternal as IPostBackEventHandler;
                if(pbeh != null)
                    return pbeh;
                pbeh = this as IPostBackEventHandler; 
                return pbeh;
            } 
        } 

        #region IControlDesignerAccessor implementation 

        /// 
        IDictionary IControlDesignerAccessor.UserData {
            get { 
                ControlRareFields rareFields = RareFieldsEnsured;
                if (rareFields.ControlDesignerAccessorUserData == null) { 
                    rareFields.ControlDesignerAccessorUserData = new HybridDictionary(); 
                }
                return rareFields.ControlDesignerAccessorUserData; 
            }
        }

        ///  
        /// 
        ///  
        IDictionary IControlDesignerAccessor.GetDesignModeState() { 
            return GetDesignModeState();
        } 


        /// 
        ///  
        /// 
        void IControlDesignerAccessor.SetDesignModeState(IDictionary data) { 
            SetDesignModeState(data); 
        }
 
        void IControlDesignerAccessor.SetOwnerControl(Control owner) {
            if (owner == this) {
                throw new ArgumentException(SR.GetString(SR.Control_CannotOwnSelf), "owner");
            } 
            OwnerControl = owner;
            _parent = owner.Parent; 
            _page = owner.Page; 
        }
        #endregion 

        #region IControlBuilderAccessor implementation

        ///  
        /// 
        /// A reference to the ControlBuilder that was used to construct this control (if there was one) 
        ///  
        [
        Browsable(false), 
        DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)
        ]
        ControlBuilder IControlBuilderAccessor.ControlBuilder {
            get { 
                return RareFields != null ? RareFields.ControlBuilder : null;
            } 
        } 
        #endregion IControlBuilderAccessor implementation
 
        #region IExpressionsAccessor


        ///  
        bool IExpressionsAccessor.HasExpressions {
            get { 
                if (RareFields == null) { 
                    return false;
                } 
                ExpressionBindingCollection expressions = RareFields.ExpressionBindings;
                return ((expressions != null) && (expressions.Count > 0));
            }
        } 

 
        ///  
        ExpressionBindingCollection IExpressionsAccessor.Expressions {
            get { 
                ExpressionBindingCollection expressions = RareFieldsEnsured.ExpressionBindings;
                if (expressions == null) {
                    expressions = new ExpressionBindingCollection();
                    RareFields.ExpressionBindings = expressions; 
                }
                return expressions; 
            } 
        }
        #endregion 

        private sealed class ControlRareFields : IDisposable {

            internal ControlRareFields() { 
            }
            public ISite Site; 
            public RenderMethod RenderMethod; 
            // Reference to the ControlBuilder used to build this control
            public ControlBuilder ControlBuilder; 
            public DataBindingCollection DataBindings;
            public Control OwnerControl;
            public ExpressionBindingCollection ExpressionBindings;
            public bool RequiredControlState = false; 

            // These fields are only used in the designer so we 
            // keep them here to prevent memory bloat at runtime 
            public IDictionary ControlDesignerAccessorUserData;
            public IDictionary DesignModeState; 

            public Version RenderingCompatibility;
            public RouteCollection RouteCollection;
            public ControlAdapter Adapter; 

            public void Dispose() { 
                //do not null out for backwards compat, VSWhidbey 475940 
                //Site = null;
                //RenderMethod = null; 
                //DataBindings = null;
                //OwnerControl = null;
                //ExpressionBindings = null;
                //Adapter = null; 
                ControlBuilder = null;
                if (OwnerControl != null) 
                { 
                    OwnerControl.Dispose();
                } 
                ControlDesignerAccessorUserData = null;
                DesignModeState = null;
                RenderingCompatibility = null;
                RouteCollection = null; 
            }
        } 
 
        private sealed class OccasionalFields : IDisposable {
            internal OccasionalFields() { 
            }

            public string SkinId;
            public IDictionary ControlsViewState; 
            public int NamedControlsID;
            // Only used if we are a naming container.  It contains all the controls 
            // in the namespace. 
            public IDictionary NamedControls;
            public ControlRareFields RareFields; 
            public String UniqueIDPrefix;

            public string SpacerImageUrl;
            public TemplateControl TemplateControl; 
            public VirtualPath TemplateSourceVirtualDirectory;
 
            public void Dispose() { 
                if (RareFields != null) {
                    RareFields.Dispose(); 
                }

                ControlsViewState = null;
                //do not null out for backwards compat, VSWhidbey 475940 
                //NamedControls = null;
                //UniqueIDPrefix = null; 
                //TemplateControl = null; 
                //TemplateSourceVirtualDirectory = null;
            } 
        }
    }
}

// File provided for Reference Use Only by Microsoft Corporation (c) 2007.

                        

Link Menu

Network programming in C#, Network Programming in VB.NET, Network Programming in .NET
This book is available now!
Buy at Amazon US or
Buy at Amazon UK