System.Net.Cache.HttpRequestCacheValidator.FetchCacheControl C# (CSharp) Method

FetchCacheControl() private method

private FetchCacheControl ( string s, bool forCache ) : void
s string
forCache bool
return void
        private unsafe void FetchCacheControl(string s, bool forCache) {
            //Initialize it
            ResponseCacheControl control = new ResponseCacheControl();
            if (forCache) {
                CacheCacheControl = control;
            }
            else {
                ResponseCacheControl = control;
            }

            if (s != null && s.Length != 0) {
                fixed (char *sp = s) {
                    int len = s.Length;
                    for (int i = 0; i < len-4; ++i) {
                        if (sp[i] < ' ' || sp[i] >= 0x7F) {
                            if(Logging.On)Logging.PrintError(Logging.RequestCache, SR.GetString(SR.net_log_cache_cache_control_error, s));
                            //invalid format
                            return;
                        }
                        if (sp[i] == ' ' || sp[i] == ',') {
                            continue;
                        }

                        // These if-else are two logically identical blocks that differ only in the way of how text search is done.
                        // The text search is done differently for 32 and X-bits platforms.
                        // ATTN: You are responsible for keeping the rest of the logic in sync.
                        if (IntPtr.Size == 4) {
                            // We are on 32-bits platform

                            long *mask = (long*)&(sp[i]);
                            //making interested chars lowercase, others are ignored anyway
                            switch(*mask|LO) {

                                case _prox: if (i+16 > len) continue;
                                    if ((*(mask+1)|LO) != _y_re || (*(mask+2)|LO) != _vali || (*(mask+3)|LO) != _date) continue;
                                    control.ProxyRevalidate = true;
                                    i+=15;
                                    break;

                                case _publ: if (i+6 > len) return;
                                    if ((*((int*)(mask+1))|LOI) != _ic) continue;
                                    control.Public = true;
                                    i+=5;
                                    break;

                                case _priv: if (i+7 > len) return;
                                    if ((*((int*)(mask+1))|LOI) != _at || (sp[i+6]|0x20) != 'e') continue;
                                    control.Private = true;
                                    i+=6;
                                    // Check for a case: private = "name1,name2"
                                    while (i < len && sp[i] == ' ') {++i;}

                                    if (i >= len || sp[i] != '=') {--i;break;}

                                    while (i < len && sp[++i] == ' ') {;}

                                    if (i >= len || sp[i] != '\"') {--i;break;}

                                    System.Collections.ArrayList privateList = new System.Collections.ArrayList();
                                    ++i;
                                    while(i < len && sp[i] != '\"') {

                                        while (i < len && sp[i] == ' ') {++i;}
                                        int start = i;
                                        while (i < len && sp[i] != ' ' && sp[i] != ',' && sp[i] != '\"') {++i;}
                                        if (start != i) {
                                            privateList.Add(s.Substring(start, i-start));
                                        }
                                        while (i < len && sp[i] != ',' && sp[i] != '\"') {++i;}
                                    }
                                    if (privateList.Count != 0) {
                                        control.PrivateHeaders = (string[])privateList.ToArray(typeof(string));
                                    }
                                    break;

                                case _no_c: if (i+8 > len) return;
                                    if ((*(mask+1)|LOI) != _ache) continue;
                                    control.NoCache = true;
                                    i+=7;
                                    // Check for a case: no-cache = "name1,name2"
                                    while (i < len && sp[i] == ' ') {++i;}

                                    if (i >= len || sp[i] != '=') {--i;break;}

                                    while (i < len && sp[++i] == ' ') {;}

                                    if (i >= len || sp[i] != '\"') {--i;break;}

                                    System.Collections.ArrayList nocacheList = new System.Collections.ArrayList();
                                    ++i;
                                    while(i < len && sp[i] != '\"') {

                                        while (i < len && sp[i] == ' ') {++i;}
                                        int start = i;
                                        while (i < len && sp[i] != ' ' && sp[i] != ',' && sp[i] != '\"') {++i;}
                                        if (start != i) {
                                            nocacheList.Add(s.Substring(start, i-start));
                                        }
                                        while (i < len && sp[i] != ',' && sp[i] != '\"') {++i;}
                                    }
                                    if (nocacheList.Count != 0) {
                                        control.NoCacheHeaders = (string[])nocacheList.ToArray(typeof(string));
                                    }
                                    break;

                                case _no_s: if (i+8 > len) return;
                                    if ((*(mask+1)|LOI) != _tore) continue;
                                    control.NoStore = true;
                                    i+=7;
                                    break;

                                case _must: if (i+15 > len) continue;

                                    if ((*(mask+1)|LO) != __rev || (*(mask+2)|LO) != _alid || (*(int*)(mask+3)|LOI) != _at || (sp[i+14]|0x20) != 'e') continue;
                                    control.MustRevalidate = true;
                                    i+=14;
                                    break;

                                case _max_: if (i+7 > len) return;
                                    if ((*((int*)(mask+1))|LOI) != _ag || (sp[i+6]|0x20) != 'e') continue;
                                    i+=7;
                                    while (i < len && sp[i] == ' ') {
                                        ++i;
                                    }
                                    if (i == len || sp[i++] != '=') return;
                                    while (i < len && sp[i] == ' ') {
                                        ++i;
                                    }
                                    if (i == len) return;
                                    control.MaxAge = 0;
                                    while (i < len && sp[i] >= '0' && sp[i] <= '9') {
                                        control.MaxAge =control.MaxAge*10 + (sp[i++]-'0');
                                    }
                                    --i;
                                    break;

                                case _s_ma: if (i+8 > len) return;
                                    if ((*(mask+1)|LOI) != _xage) continue;
                                    i+=8;
                                    while (i < len && sp[i] == ' ') {
                                        ++i;
                                    }
                                    if (i == len || sp[i++] != '=') return;
                                    while (i < len && sp[i] == ' ') {
                                        ++i;
                                    }
                                    if (i == len) return;
                                    control.SMaxAge = 0;
                                    while (i < len && sp[i] >= '0' && sp[i] <= '9') {
                                        control.SMaxAge = control.SMaxAge*10 + (sp[i++]-'0');
                                    }
                                    --i;
                                    break;
                            }
                        }
                        else {
                            if (Rfc2616.Common.UnsafeAsciiLettersNoCaseEqual(sp, i, len, "proxy-revalidate")) {
                                control.ProxyRevalidate = true;
                                i+=15;
                            }
                            else if (Rfc2616.Common.UnsafeAsciiLettersNoCaseEqual(sp, i, len, "public")) {
                                control.Public = true;
                                i+=5;
                            }
                            else if (Rfc2616.Common.UnsafeAsciiLettersNoCaseEqual(sp, i, len, "private")) {
                                control.Private = true;
                                i+=6;
                                // Check for a case: private = "name1,name2"
                                while (i < len && sp[i] == ' ') {++i;}

                                if (i >= len || sp[i] != '=') {--i;break;}

                                while (i < len && sp[++i] == ' ') {;}

                                if (i >= len || sp[i] != '\"') {--i;break;}

                                System.Collections.ArrayList privateList = new System.Collections.ArrayList();
                                ++i;
                                while(i < len && sp[i] != '\"') {

                                    while (i < len && sp[i] == ' ') {++i;}
                                    int start = i;
                                    while (i < len && sp[i] != ' ' && sp[i] != ',' && sp[i] != '\"') {++i;}
                                    if (start != i) {
                                        privateList.Add(s.Substring(start, i-start));
                                    }
                                    while (i < len && sp[i] != ',' && sp[i] != '\"') {++i;}
                                }
                                if (privateList.Count != 0) {
                                    control.PrivateHeaders = (string[])privateList.ToArray(typeof(string));
                                }
                            }
                            else if (Rfc2616.Common.UnsafeAsciiLettersNoCaseEqual(sp, i, len, "no-cache")) {
                                control.NoCache = true;
                                i+=7;
                                // Check for a case: no-cache = "name1,name2"
                                while (i < len && sp[i] == ' ') {++i;}

                                if (i >= len || sp[i] != '=') {--i;break;}

                                while (i < len && sp[++i] == ' ') {;}

                                if (i >= len || sp[i] != '\"') {--i;break;}

                                System.Collections.ArrayList nocacheList = new System.Collections.ArrayList();
                                ++i;
                                while(i < len && sp[i] != '\"') {

                                    while (i < len && sp[i] == ' ') {++i;}
                                    int start = i;
                                    while (i < len && sp[i] != ' ' && sp[i] != ',' && sp[i] != '\"') {++i;}
                                    if (start != i) {
                                        nocacheList.Add(s.Substring(start, i-start));
                                    }
                                    while (i < len && sp[i] != ',' && sp[i] != '\"') {++i;}
                                }
                                if (nocacheList.Count != 0) {
                                    control.NoCacheHeaders = (string[])nocacheList.ToArray(typeof(string));
                                }
                            }
                            else if (Rfc2616.Common.UnsafeAsciiLettersNoCaseEqual(sp, i, len, "no-store")) {
                                control.NoStore = true;
                                i+=7;
                            }
                            else if (Rfc2616.Common.UnsafeAsciiLettersNoCaseEqual(sp, i, len, "must-revalidate")) {
                                control.MustRevalidate = true;
                                i+=14;
                            }
                            else if (Rfc2616.Common.UnsafeAsciiLettersNoCaseEqual(sp, i, len, "max-age")) {
                                i+=7;
                                while (i < len && sp[i] == ' ') {
                                    ++i;
                                }
                                if (i == len || sp[i++] != '=') return;
                                while (i < len && sp[i] == ' ') {
                                    ++i;
                                }
                                if (i == len) return;
                                control.MaxAge = 0;
                                while (i < len && sp[i] >= '0' && sp[i] <= '9') {
                                    control.MaxAge =control.MaxAge*10 + (sp[i++]-'0');
                                }
                                --i;
                            }
                            else if (Rfc2616.Common.UnsafeAsciiLettersNoCaseEqual(sp, i, len, "smax-age")) {
                                i+=8;
                                while (i < len && sp[i] == ' ') {
                                    ++i;
                                }
                                if (i == len || sp[i++] != '=') return;
                                while (i < len && sp[i] == ' ') {
                                    ++i;
                                }
                                if (i == len) return;
                                control.SMaxAge = 0;
                                while (i < len && sp[i] >= '0' && sp[i] <= '9') {
                                    control.SMaxAge = control.SMaxAge*10 + (sp[i++]-'0');
                                }
                                --i;
                            }
                        }
                    }
                }
            }
        }