internal bool IsSupersetOf(DBConnectionString entry) { switch (this._behavior) { case KeyRestrictionBehavior.AllowOnly: for (NameValuePair pair = entry.KeyChain; pair != null; pair = pair.Next) { if (!this.ContainsKey(pair.Name) && this.IsRestrictedKeyword(pair.Name)) { return(false); } } break; case KeyRestrictionBehavior.PreventUsage: if (this._restrictionValues != null) { foreach (string str in this._restrictionValues) { if (entry.ContainsKey(str)) { return(false); } } } break; default: throw ADP.InvalidKeyRestrictionBehavior(this._behavior); } return(true); }
internal bool IsSupersetOf(DBConnectionString entry) { Debug.Assert(!_hasPassword || ContainsKey(KEY.Password) || ContainsKey(KEY.Pwd), "OnDeserialized password mismatch this"); Debug.Assert(!entry._hasPassword || entry.ContainsKey(KEY.Password) || entry.ContainsKey(KEY.Pwd), "OnDeserialized password mismatch entry"); switch (_behavior) { case KeyRestrictionBehavior.AllowOnly: // every key must either be in the resticted connection string or in the allowed keywords // keychain may contain duplicates, but it is better than GetEnumerator on _parsetable.Keys for (NameValuePair current = entry.KeyChain; null != current; current = current.Next) { if (!ContainsKey(current.Name) && IsRestrictedKeyword(current.Name)) { return(false); } } break; case KeyRestrictionBehavior.PreventUsage: // every key can not be in the restricted keywords (even if in the restricted connection string) if (null != _restrictionValues) { foreach (string restriction in _restrictionValues) { if (entry.ContainsKey(restriction)) { return(false); } } } break; default: Debug.Assert(false, "invalid KeyRestrictionBehavior"); throw ADP.InvalidKeyRestrictionBehavior(_behavior); } return(true); }
internal bool CheckValueForKeyPermit(DBConnectionString parsetable) { if (parsetable == null) { return(false); } bool isEmpty = false; NameValuePermission[] permissionArray = this._tree; if (permissionArray != null) { isEmpty = parsetable.IsEmpty; if (!isEmpty) { for (int i = 0; i < permissionArray.Length; i++) { NameValuePermission permission = permissionArray[i]; if (permission != null) { string keyword = permission._value; if (parsetable.ContainsKey(keyword)) { string keyInQuestion = parsetable[keyword]; NameValuePermission permission2 = permission.CheckKeyForValue(keyInQuestion); if ((permission2 != null) && permission2.CheckValueForKeyPermit(parsetable)) { isEmpty = true; } else { return(false); } } } } } } DBConnectionString str = this._entry; if (str != null) { isEmpty = str.IsSupersetOf(parsetable); } return(isEmpty); }
internal bool CheckValueForKeyPermit(DBConnectionString parsetable) { if (null == parsetable) { return(false); } bool hasMatch = false; NameValuePermission[] keytree = _tree; // _tree won't mutate but Add will replace it if (null != keytree) { hasMatch = parsetable.IsEmpty; // MDAC 86773 if (!hasMatch) { // which key do we follow the key-value chain on for (int i = 0; i < keytree.Length; ++i) { NameValuePermission permitKey = keytree[i]; if (null != permitKey) { string keyword = permitKey._value; #if DEBUG Debug.Assert(null == permitKey._entry, "key member has no restrictions"); #endif if (parsetable.ContainsKey(keyword)) { string valueInQuestion = (string)parsetable[keyword]; // keyword is restricted to certain values NameValuePermission permitValue = permitKey.CheckKeyForValue(valueInQuestion); if (null != permitValue) { //value does match - continue the chain down that branch if (permitValue.CheckValueForKeyPermit(parsetable)) { hasMatch = true; // adding a break statement is tempting, but wrong // user can safetly extend their restrictions for current rule to include missing keyword // i.e. Add("provider=sqloledb;integrated security=sspi", "data provider=", KeyRestrictionBehavior.AllowOnly); // i.e. Add("data provider=msdatashape;provider=sqloledb;integrated security=sspi", "", KeyRestrictionBehavior.AllowOnly); } else { // failed branch checking return(false); } } else { // value doesn't match to expected values - fail here return(false); } } } // else try next keyword } } // partial chain match, either leaf-node by shorter chain or fail mid-chain if (null == _restrictions) } DBConnectionString entry = _entry; if (null != entry) { // also checking !hasMatch is tempting, but wrong // user can safetly extend their restrictions for current rule to include missing keyword // i.e. Add("provider=sqloledb;integrated security=sspi", "data provider=", KeyRestrictionBehavior.AllowOnly); // i.e. Add("provider=sqloledb;", "integrated security=;", KeyRestrictionBehavior.AllowOnly); hasMatch = entry.IsSupersetOf(parsetable); } return(hasMatch); // mid-chain failure }
internal DBConnectionString Intersect(DBConnectionString entry) { KeyRestrictionBehavior behavior = _behavior; string[] restrictionValues = null; if (null == entry) { //Debug.WriteLine("0 entry AllowNothing"); behavior = KeyRestrictionBehavior.AllowOnly; } else if (this._behavior != entry._behavior) // subset of the AllowOnly array { behavior = KeyRestrictionBehavior.AllowOnly; if (KeyRestrictionBehavior.AllowOnly == entry._behavior) // this PreventUsage and entry AllowOnly { if (!ADP.IsEmptyArray(_restrictionValues)) { if (!ADP.IsEmptyArray(entry._restrictionValues)) { //Debug.WriteLine("1 this PreventUsage with restrictions and entry AllowOnly with restrictions"); restrictionValues = NewRestrictionAllowOnly(entry._restrictionValues, _restrictionValues); } else { //Debug.WriteLine("2 this PreventUsage with restrictions and entry AllowOnly with no restrictions"); } } else { //Debug.WriteLine("3/4 this PreventUsage with no restrictions and entry AllowOnly"); restrictionValues = entry._restrictionValues; } } else if (!ADP.IsEmptyArray(_restrictionValues)) // this AllowOnly and entry PreventUsage { if (!ADP.IsEmptyArray(entry._restrictionValues)) { //Debug.WriteLine("5 this AllowOnly with restrictions and entry PreventUsage with restrictions"); restrictionValues = NewRestrictionAllowOnly(_restrictionValues, entry._restrictionValues); } else { //Debug.WriteLine("6 this AllowOnly and entry PreventUsage with no restrictions"); restrictionValues = _restrictionValues; } } else { //Debug.WriteLine("7/8 this AllowOnly with no restrictions and entry PreventUsage"); } } else if (KeyRestrictionBehavior.PreventUsage == this._behavior) // both PreventUsage { if (ADP.IsEmptyArray(_restrictionValues)) { //Debug.WriteLine("9/10 both PreventUsage and this with no restrictions"); restrictionValues = entry._restrictionValues; } else if (ADP.IsEmptyArray(entry._restrictionValues)) { //Debug.WriteLine("11 both PreventUsage and entry with no restrictions"); restrictionValues = _restrictionValues; } else { //Debug.WriteLine("12 both PreventUsage with restrictions"); restrictionValues = NoDuplicateUnion(_restrictionValues, entry._restrictionValues); } } else if (!ADP.IsEmptyArray(_restrictionValues) && !ADP.IsEmptyArray(entry._restrictionValues)) // both AllowOnly with restrictions { if (this._restrictionValues.Length <= entry._restrictionValues.Length) { //Debug.WriteLine("13a this AllowOnly with restrictions and entry AllowOnly with restrictions"); restrictionValues = NewRestrictionIntersect(_restrictionValues, entry._restrictionValues); } else { //Debug.WriteLine("13b this AllowOnly with restrictions and entry AllowOnly with restrictions"); restrictionValues = NewRestrictionIntersect(entry._restrictionValues, _restrictionValues); } } else // both AllowOnly //Debug.WriteLine("14/15/16 this AllowOnly and entry AllowOnly but no restrictions"); { } // verify _hasPassword & _parsetable are in sync between Everett/Whidbey Debug.Assert(!_hasPassword || ContainsKey(KEY.Password) || ContainsKey(KEY.Pwd), "OnDeserialized password mismatch this"); Debug.Assert(null == entry || !entry._hasPassword || entry.ContainsKey(KEY.Password) || entry.ContainsKey(KEY.Pwd), "OnDeserialized password mismatch entry"); DBConnectionString value = new DBConnectionString(this, restrictionValues, behavior); ValidateCombinedSet(this, value); ValidateCombinedSet(entry, value); return(value); }
internal bool IsSupersetOf(DBConnectionString entry) { Debug.Assert(!_hasPassword || ContainsKey(KEY.Password) || ContainsKey(KEY.Pwd), "OnDeserialized password mismatch this"); Debug.Assert(!entry._hasPassword || entry.ContainsKey(KEY.Password) || entry.ContainsKey(KEY.Pwd), "OnDeserialized password mismatch entry"); switch(_behavior) { case KeyRestrictionBehavior.AllowOnly: // every key must either be in the resticted connection string or in the allowed keywords // keychain may contain duplicates, but it is better than GetEnumerator on _parsetable.Keys for(NameValuePair current = entry.KeyChain; null != current; current = current.Next) { if (!ContainsKey(current.Name) && IsRestrictedKeyword(current.Name)) { return false; } } break; case KeyRestrictionBehavior.PreventUsage: // every key can not be in the restricted keywords (even if in the restricted connection string) if (null != _restrictionValues) { foreach(string restriction in _restrictionValues) { if (entry.ContainsKey(restriction)) { return false; } } } break; default: Debug.Assert(false, "invalid KeyRestrictionBehavior"); throw ADP.InvalidKeyRestrictionBehavior(_behavior); } return true; }
internal DBConnectionString Intersect(DBConnectionString entry) { KeyRestrictionBehavior behavior = _behavior; string[] restrictionValues = null; if (null == entry) { //Debug.WriteLine("0 entry AllowNothing"); behavior = KeyRestrictionBehavior.AllowOnly; } else if (this._behavior != entry._behavior) { // subset of the AllowOnly array behavior = KeyRestrictionBehavior.AllowOnly; if (KeyRestrictionBehavior.AllowOnly == entry._behavior) { // this PreventUsage and entry AllowOnly if (!ADP.IsEmptyArray(_restrictionValues)) { if (!ADP.IsEmptyArray(entry._restrictionValues)) { //Debug.WriteLine("1 this PreventUsage with restrictions and entry AllowOnly with restrictions"); restrictionValues = NewRestrictionAllowOnly(entry._restrictionValues, _restrictionValues); } else { //Debug.WriteLine("2 this PreventUsage with restrictions and entry AllowOnly with no restrictions"); } } else { //Debug.WriteLine("3/4 this PreventUsage with no restrictions and entry AllowOnly"); restrictionValues = entry._restrictionValues; } } else if (!ADP.IsEmptyArray(_restrictionValues)) { // this AllowOnly and entry PreventUsage if (!ADP.IsEmptyArray(entry._restrictionValues)) { //Debug.WriteLine("5 this AllowOnly with restrictions and entry PreventUsage with restrictions"); restrictionValues = NewRestrictionAllowOnly(_restrictionValues, entry._restrictionValues); } else { //Debug.WriteLine("6 this AllowOnly and entry PreventUsage with no restrictions"); restrictionValues = _restrictionValues; } } else { //Debug.WriteLine("7/8 this AllowOnly with no restrictions and entry PreventUsage"); } } else if (KeyRestrictionBehavior.PreventUsage == this._behavior) { // both PreventUsage if (ADP.IsEmptyArray(_restrictionValues)) { //Debug.WriteLine("9/10 both PreventUsage and this with no restrictions"); restrictionValues = entry._restrictionValues; } else if (ADP.IsEmptyArray(entry._restrictionValues)) { //Debug.WriteLine("11 both PreventUsage and entry with no restrictions"); restrictionValues = _restrictionValues; } else { //Debug.WriteLine("12 both PreventUsage with restrictions"); restrictionValues = NoDuplicateUnion(_restrictionValues, entry._restrictionValues); } } else if (!ADP.IsEmptyArray(_restrictionValues) && !ADP.IsEmptyArray(entry._restrictionValues)) { // both AllowOnly with restrictions if (this._restrictionValues.Length <= entry._restrictionValues.Length) { //Debug.WriteLine("13a this AllowOnly with restrictions and entry AllowOnly with restrictions"); restrictionValues = NewRestrictionIntersect(_restrictionValues, entry._restrictionValues); } else { //Debug.WriteLine("13b this AllowOnly with restrictions and entry AllowOnly with restrictions"); restrictionValues = NewRestrictionIntersect(entry._restrictionValues, _restrictionValues); } } else { // both AllowOnly //Debug.WriteLine("14/15/16 this AllowOnly and entry AllowOnly but no restrictions"); } // verify _hasPassword & _parsetable are in sync between Everett/Whidbey Debug.Assert(!_hasPassword || ContainsKey(KEY.Password) || ContainsKey(KEY.Pwd), "OnDeserialized password mismatch this"); Debug.Assert(null == entry || !entry._hasPassword || entry.ContainsKey(KEY.Password) || entry.ContainsKey(KEY.Pwd), "OnDeserialized password mismatch entry"); DBConnectionString value = new DBConnectionString(this, restrictionValues, behavior); ValidateCombinedSet(this, value); ValidateCombinedSet(entry, value); return value; }
internal bool CheckValueForKeyPermit(DBConnectionString parsetable) { if (null == parsetable) { return false; } bool hasMatch = false; NameValuePermission[] keytree = _tree; // _tree won't mutate but Add will replace it if (null != keytree) { hasMatch = parsetable.IsEmpty; // MDAC 86773 if (!hasMatch) { // which key do we follow the key-value chain on for (int i = 0; i < keytree.Length; ++i) { NameValuePermission permitKey = keytree[i]; if (null != permitKey) { string keyword = permitKey._value; #if DEBUG Debug.Assert(null == permitKey._entry, "key member has no restrictions"); #endif if (parsetable.ContainsKey(keyword)) { string valueInQuestion = (string)parsetable[keyword]; // keyword is restricted to certain values NameValuePermission permitValue = permitKey.CheckKeyForValue(valueInQuestion); if (null != permitValue) { //value does match - continue the chain down that branch if (permitValue.CheckValueForKeyPermit(parsetable)) { hasMatch = true; // adding a break statement is tempting, but wrong // user can safetly extend their restrictions for current rule to include missing keyword // i.e. Add("provider=sqloledb;integrated security=sspi", "data provider=", KeyRestrictionBehavior.AllowOnly); // i.e. Add("data provider=msdatashape;provider=sqloledb;integrated security=sspi", "", KeyRestrictionBehavior.AllowOnly); } else { // failed branch checking return false; } } else { // value doesn't match to expected values - fail here return false; } } } // else try next keyword } } // partial chain match, either leaf-node by shorter chain or fail mid-chain if (null == _restrictions) } DBConnectionString entry = _entry; if (null != entry) { // also checking !hasMatch is tempting, but wrong // user can safetly extend their restrictions for current rule to include missing keyword // i.e. Add("provider=sqloledb;integrated security=sspi", "data provider=", KeyRestrictionBehavior.AllowOnly); // i.e. Add("provider=sqloledb;", "integrated security=;", KeyRestrictionBehavior.AllowOnly); hasMatch = entry.IsSupersetOf(parsetable); } return hasMatch; // mid-chain failure }
internal DBConnectionString Intersect(DBConnectionString entry) { KeyRestrictionBehavior behavior = _behavior; string[] restrictionValues = null; if (null == entry) { behavior = KeyRestrictionBehavior.AllowOnly; } else if (_behavior != entry._behavior) { // subset of the AllowOnly array behavior = KeyRestrictionBehavior.AllowOnly; if (KeyRestrictionBehavior.AllowOnly == entry._behavior) { // this PreventUsage and entry AllowOnly if (!ADP.IsEmptyArray(_restrictionValues)) { if (!ADP.IsEmptyArray(entry._restrictionValues)) { restrictionValues = NewRestrictionAllowOnly(entry._restrictionValues, _restrictionValues); } } else { restrictionValues = entry._restrictionValues; } } else if (!ADP.IsEmptyArray(_restrictionValues)) { // this AllowOnly and entry PreventUsage if (!ADP.IsEmptyArray(entry._restrictionValues)) { restrictionValues = NewRestrictionAllowOnly(_restrictionValues, entry._restrictionValues); } else { restrictionValues = _restrictionValues; } } } else if (KeyRestrictionBehavior.PreventUsage == _behavior) { // both PreventUsage if (ADP.IsEmptyArray(_restrictionValues)) { restrictionValues = entry._restrictionValues; } else if (ADP.IsEmptyArray(entry._restrictionValues)) { restrictionValues = _restrictionValues; } else { restrictionValues = NoDuplicateUnion(_restrictionValues, entry._restrictionValues); } } else if (!ADP.IsEmptyArray(_restrictionValues) && !ADP.IsEmptyArray(entry._restrictionValues)) { // both AllowOnly with restrictions if (_restrictionValues.Length <= entry._restrictionValues.Length) { restrictionValues = NewRestrictionIntersect(_restrictionValues, entry._restrictionValues); } else { restrictionValues = NewRestrictionIntersect(entry._restrictionValues, _restrictionValues); } } // verify _hasPassword & _parsetable are in sync between Everett/Whidbey Debug.Assert(!_hasPassword || ContainsKey(KEY.Password) || ContainsKey(KEY.Pwd), "OnDeserialized password mismatch this"); Debug.Assert(null == entry || !entry._hasPassword || entry.ContainsKey(KEY.Password) || entry.ContainsKey(KEY.Pwd), "OnDeserialized password mismatch entry"); DBConnectionString value = new DBConnectionString(this, restrictionValues, behavior); ValidateCombinedSet(this, value); ValidateCombinedSet(entry, value); return(value); }