private string GetUriPartsFromUserString(UriComponents uriParts)
{
ushort delimiterAwareIdx;
switch (uriParts & ~UriComponents.KeepDelimiter)
{
// For FindServicePoint perf
case UriComponents.Scheme | UriComponents.Host | UriComponents.Port:
if (!InFact(Flags.HasUserInfo))
return _string.Substring(_info.Offset.Scheme, _info.Offset.Path - _info.Offset.Scheme);
return _string.Substring(_info.Offset.Scheme, _info.Offset.User - _info.Offset.Scheme)
+ _string.Substring(_info.Offset.Host, _info.Offset.Path - _info.Offset.Host);
// For HttpWebRequest.ConnectHostAndPort perf
case UriComponents.HostAndPort: //Host|StrongPort
if (!InFact(Flags.HasUserInfo))
goto case UriComponents.StrongAuthority;
if (InFact(Flags.NotDefaultPort) || _syntax.DefaultPort == UriParser.NoDefaultPort)
return _string.Substring(_info.Offset.Host, _info.Offset.Path - _info.Offset.Host);
return _string.Substring(_info.Offset.Host, _info.Offset.Path - _info.Offset.Host)
+ ':' + _info.Offset.PortValue.ToString(CultureInfo.InvariantCulture);
// For an obvious common case perf
case UriComponents.AbsoluteUri: //Scheme|UserInfo|Host|Port|Path|Query|Fragment,
if (_info.Offset.Scheme == 0 && _info.Offset.End == _string.Length)
return _string;
return _string.Substring(_info.Offset.Scheme, _info.Offset.End - _info.Offset.Scheme);
// For Uri.Equals() and HttpWebRequest through a proxy perf
case UriComponents.HttpRequestUrl: //Scheme|Host|Port|Path|Query,
if (InFact(Flags.HasUserInfo))
{
return _string.Substring(_info.Offset.Scheme, _info.Offset.User - _info.Offset.Scheme)
+ _string.Substring(_info.Offset.Host, _info.Offset.Fragment - _info.Offset.Host);
}
if (_info.Offset.Scheme == 0 && _info.Offset.Fragment == _string.Length)
return _string;
return _string.Substring(_info.Offset.Scheme, _info.Offset.Fragment - _info.Offset.Scheme);
// For CombineUri() perf
case UriComponents.SchemeAndServer | UriComponents.UserInfo:
return _string.Substring(_info.Offset.Scheme, _info.Offset.Path - _info.Offset.Scheme);
// For Cache perf
case (UriComponents.AbsoluteUri & ~UriComponents.Fragment):
if (_info.Offset.Scheme == 0 && _info.Offset.Fragment == _string.Length)
return _string;
return _string.Substring(_info.Offset.Scheme, _info.Offset.Fragment - _info.Offset.Scheme);
// Strip scheme delimiter if was not requested
case UriComponents.Scheme:
if (uriParts != UriComponents.Scheme)
return _string.Substring(_info.Offset.Scheme, _info.Offset.User - _info.Offset.Scheme);
return _syntax.SchemeName;
// KeepDelimiter makes no sense for this component
case UriComponents.Host:
ushort idx = _info.Offset.Path;
if (InFact(Flags.NotDefaultPort | Flags.PortNotCanonical))
{
//Means we do have ':' after the host
while (_string[--idx] != ':')
;
}
return (idx - _info.Offset.Host == 0) ? string.Empty : _string.Substring(_info.Offset.Host,
idx - _info.Offset.Host);
case UriComponents.Path:
// Strip the leading '/' for a hierarchical URI if no delimiter was requested
if (uriParts == UriComponents.Path && InFact(Flags.AuthorityFound) &&
_info.Offset.End > _info.Offset.Path && _string[_info.Offset.Path] == '/')
delimiterAwareIdx = (ushort)(_info.Offset.Path + 1);
else
delimiterAwareIdx = _info.Offset.Path;
if (delimiterAwareIdx >= _info.Offset.Query)
return string.Empty;
return _string.Substring(delimiterAwareIdx, _info.Offset.Query - delimiterAwareIdx);
case UriComponents.Query:
// Strip the '?' if no delimiter was requested
if (uriParts == UriComponents.Query)
delimiterAwareIdx = (ushort)(_info.Offset.Query + 1);
else
delimiterAwareIdx = _info.Offset.Query;
if (delimiterAwareIdx >= _info.Offset.Fragment)
return string.Empty;
return _string.Substring(delimiterAwareIdx, _info.Offset.Fragment - delimiterAwareIdx);
case UriComponents.Fragment:
// Strip the '#' if no delimiter was requested
if (uriParts == UriComponents.Fragment)
delimiterAwareIdx = (ushort)(_info.Offset.Fragment + 1);
else
delimiterAwareIdx = _info.Offset.Fragment;
if (delimiterAwareIdx >= _info.Offset.End)
return string.Empty;
return _string.Substring(delimiterAwareIdx, _info.Offset.End - delimiterAwareIdx);
case UriComponents.UserInfo | UriComponents.Host | UriComponents.Port:
return (_info.Offset.Path - _info.Offset.User == 0) ? string.Empty :
_string.Substring(_info.Offset.User, _info.Offset.Path - _info.Offset.User);
case UriComponents.StrongAuthority: //UserInfo|Host|StrongPort
if (InFact(Flags.NotDefaultPort) || _syntax.DefaultPort == UriParser.NoDefaultPort)
goto case UriComponents.UserInfo | UriComponents.Host | UriComponents.Port;
return _string.Substring(_info.Offset.User, _info.Offset.Path - _info.Offset.User)
+ ':' + _info.Offset.PortValue.ToString(CultureInfo.InvariantCulture);
case UriComponents.PathAndQuery: //Path|Query,
return _string.Substring(_info.Offset.Path, _info.Offset.Fragment - _info.Offset.Path);
case UriComponents.HttpRequestUrl | UriComponents.Fragment: //Scheme|Host|Port|Path|Query|Fragment,
if (InFact(Flags.HasUserInfo))
{
return _string.Substring(_info.Offset.Scheme, _info.Offset.User - _info.Offset.Scheme)
+ _string.Substring(_info.Offset.Host, _info.Offset.End - _info.Offset.Host);
}
if (_info.Offset.Scheme == 0 && _info.Offset.End == _string.Length)
return _string;
return _string.Substring(_info.Offset.Scheme, _info.Offset.End - _info.Offset.Scheme);
case UriComponents.PathAndQuery | UriComponents.Fragment: //LocalUrl|Fragment
return _string.Substring(_info.Offset.Path, _info.Offset.End - _info.Offset.Path);
case UriComponents.UserInfo:
// Strip the '@' if no delimiter was requested
if (NotAny(Flags.HasUserInfo))
return string.Empty;
if (uriParts == UriComponents.UserInfo)
delimiterAwareIdx = (ushort)(_info.Offset.Host - 1);
else
delimiterAwareIdx = _info.Offset.Host;
if (_info.Offset.User >= delimiterAwareIdx)
return string.Empty;
return _string.Substring(_info.Offset.User, delimiterAwareIdx - _info.Offset.User);
default:
return null;
}
}