{"record":{"id":"fc06a54a75ee1bd4","repo":"git-ecosystem/git-credential-manager","slug":"argument-must-be-strictly-less-than-upper","errorCode":null,"errorMessage":"Argument must be strictly less than {upper}.","messagePattern":"Argument must be strictly less than (.+?)\\.","errorType":"exception","errorClass":"ArgumentOutOfRangeException","httpStatus":null,"severity":"error","filePath":"src/Core/EnsureArgument.cs","lineNumber":96,"sourceCode":"        {\n            if (lowerInclusive && arg < lower)\n            {\n                throw new ArgumentOutOfRangeException(name, $\"Argument must be greater than or equal to {lower}.\");\n            }\n\n            if (!lowerInclusive && arg <= lower)\n            {\n                throw new ArgumentOutOfRangeException(name, $\"Argument must be strictly greater than {lower}.\");\n            }\n\n            if (upperInclusive && arg > upper)\n            {\n                throw new ArgumentOutOfRangeException(name, $\"Argument must be less than or equal to {upper}.\");\n            }\n\n            if (!upperInclusive && arg >= upper)\n            {\n                throw new ArgumentOutOfRangeException(name, $\"Argument must be strictly less than {upper}.\");\n            }\n        }\n    }\n}\n","sourceCodeStart":78,"sourceCodeEnd":101,"githubUrl":"https://github.com/git-ecosystem/git-credential-manager/blob/e8ce762cd04b4100ae637b5fbf39ef9d0a96561e/src/Core/EnsureArgument.cs#L78-L101","documentation":"This ArgumentOutOfRangeException is thrown by EnsureArgument.InRange when upperInclusive is false and the argument is greater than or equal to the upper bound. With an exclusive upper bound the value must satisfy arg < upper strictly. The message interpolates the actual bound.","triggerScenarios":"Calling EnsureArgument.InRange(arg, name, lower, upper, upperInclusive: false) with arg >= upper, e.g., passing exactly the exclusive maximum, or using length as an upper bound while the range check treats it as exclusive in a way the caller did not expect.","commonSituations":"Mixing .NET conventions where some ranges are end-exclusive (Substring, Take) and passing a value equal to the end; boundary values that passed under inclusive checks before a flag change; off-by-one in loop bounds.","solutions":["Ensure the value is strictly less than upper; decrement or clamp to upper - 1 if needed","If the bound should be inclusive, pass upperInclusive: true (the default)","Align with the convention of similar APIs (e.g., end-exclusive slicing) and document it","Re-check call sites after changes to the inclusivity flags"],"exampleFix":"// before\nEnsureArgument.InRange(i, nameof(i), 0, list.Count, upperInclusive: false); // i == list.Count\n// after\nEnsureArgument.InRange(i, nameof(i), 0, list.Count); // inclusive: i == list.Count - 1 max","handlingStrategy":"validation","validationCode":"// exclusive upper bound: value must be < upper\nif (value >= upper) value = upper - 1;\nEnsureArgument.InRange(value, nameof(value), lower, upper, upperInclusive: false);","typeGuard":"static bool IsStrictlyBelow(int v, int upper) => v < upper;","tryCatchPattern":"try { EnsureArgument.InRange(i, nameof(i), 0, count, upperInclusive: false); }\ncatch (ArgumentOutOfRangeException ex)\n{\n    throw new InvalidOperationException($\"{ex.ParamName} must be < {count} (exclusive upper bound)\", ex);\n}","preventionTips":["Match end-exclusive conventions (Substring/Take-style) consistently across APIs","Pass upperInclusive: true if callers naturally supply the last valid value","Add unit tests at boundaries: upper - 1 (valid) and upper (invalid)","Document exclusivity in XML docs on the validating method"],"tags":["argument-validation","range-check","bounds"],"backgroundTag":"value-out-of-range","analyzedSha":"e8ce762cd04b4100ae637b5fbf39ef9d0a96561e","analyzedAt":"2026-09-11T17:15:08.753Z","contentChangedAt":"2026-09-11T17:15:08.753Z","schemaVersion":2},"datasetVersion":"2026-09-16T09:17:16.951Z"}